Merge
authorduke
Wed, 05 Jul 2017 20:35:10 +0200
changeset 30711 9ca8a42d1190
parent 30710 76bc0159a861 (current diff)
parent 30709 803777172064 (diff)
child 30735 11b2581a067e
Merge
hotspot/agent/src/share/classes/sun/jvm/hotspot/compiler/OopMap.java
hotspot/agent/src/share/classes/sun/jvm/hotspot/compiler/OopMapSet.java
hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/images/bytecode.gif
hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/images/link.gif
hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/images/method.gif
hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/META-INF/services/com.sun.hotspot.igv.data.services.GroupOrganizer
hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/GraphCountGroupOrganizer.java
hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/StandardGroupOrganizer.java
hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/StructuredViewAction.java
hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/diff.gif
hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/folder.gif
hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/graph.gif
hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/import.gif
hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/remove.gif
hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/removeall.gif
hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/save.gif
hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/structure.gif
hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/services/GroupOrganizer.java
hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/services/GroupReceiver.java
hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/META-INF/services/com.sun.hotspot.igv.filter.ScriptEngineAbstraction
hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/JavaSE6ScriptEngine.java
hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/NullScriptEngine.java
hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/ScriptEngineAbstraction.java
hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/images/add.gif
hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/images/delete.gif
hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/images/down.gif
hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/images/minus.gif
hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/images/plus.gif
hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/images/up.gif
hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/Source.java
hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/OldHierarchicalLayoutManager.java
hotspot/src/share/tools/IdealGraphVisualizer/NetworkConnection/src/META-INF/services/com.sun.hotspot.igv.data.services.GroupReceiver
hotspot/src/share/tools/IdealGraphVisualizer/README
hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/build.xml
hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/manifest.mf
hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/nbproject/build-impl.xml
hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/nbproject/genfiles.properties
hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/nbproject/project.properties
hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/nbproject/project.xml
hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/nbproject/suite.properties
hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/src/META-INF/services/com.sun.hotspot.igv.filter.ScriptEngineAbstraction
hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/src/com/sun/hotspot/igv/rhino/Bundle.properties
hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/src/com/sun/hotspot/igv/rhino/RhinoScriptEngine.java
hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/src/com/sun/hotspot/igv/rhino/layer.xml
hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/META-INF/services/com.sun.hotspot.igv.data.services.GroupOrganizer
hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/JavaGroupOrganizer.java
hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/combine.filter
hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/extendedColor.filter
hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/linestyle.filter
hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/removeMemory.filter
hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/removeRootInputs.filter
hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/removeSafepointInputs.filter
hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/removeSelfLoops.filter
hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/split.filter
hotspot/src/share/tools/IdealGraphVisualizer/Settings/src/com/sun/hotspot/igv/settings/settings.gif
hotspot/src/share/tools/IdealGraphVisualizer/View/src/META-INF/services/com.sun.hotspot.igv.data.services.InputGraphProvider
hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/ConnectionAnchor.java
hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/ExtendedPanAction.java
hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/FindPanel.java
hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/PreferenceConstants.java
hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/SlotLayout.java
hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/NodeFindAction.java
hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/images/export.gif
hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/images/overview.gif
hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/images/search.gif
hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/images/zoomin.gif
hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/images/zoomout.gif
hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/widgets/DiagramConnectionWidget.java
hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/widgets/MultiConnectionWidget.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/Asserts.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/BuildHelper.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/ByteCodeLoader.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/DynamicVMOption.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/ExitCode.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/InMemoryJavaCompiler.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/InfiniteLoop.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/InputArguments.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/JDKToolFinder.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/JDKToolLauncher.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/OutputAnalyzer.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/OutputBuffer.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/PerfCounter.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/PerfCounters.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/Platform.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/ProcessTools.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/StreamPumper.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/TimeLimitedRunner.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/Utils.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/cli/CPUSpecificCommandLineOptionTest.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/cli/CommandLineOptionTest.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/cli/predicate/AndPredicate.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/cli/predicate/CPUSpecificPredicate.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/cli/predicate/NotPredicate.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/cli/predicate/OrPredicate.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/dcmd/CommandExecutor.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/dcmd/CommandExecutorException.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/dcmd/FileJcmdExecutor.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/dcmd/JMXExecutor.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/dcmd/JcmdExecutor.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/dcmd/MainClassJcmdExecutor.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/dcmd/PidJcmdExecutor.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/dtrace/DtraceResultsAnalyzer.java
hotspot/test/testlibrary/com/oracle/java/testlibrary/dtrace/DtraceRunner.java
jaxp/test/javax/xml/jaxp/TEST.properties
jaxp/test/javax/xml/jaxp/unittest/javax/xml/common/Bug6979306Test.java
jaxp/test/javax/xml/jaxp/unittest/javax/xml/parsers/Bug8003147Test.java
jaxp/test/javax/xml/jaxp/unittest/javax/xml/transform/Bug6551616.java
jaxp/test/javax/xml/jaxp/unittest/javax/xml/transform/CLITest.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/Main.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/AbstractJavaHeapObjectVisitor.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/ArrayTypeCodes.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/HackJavaValue.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaBoolean.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaByte.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaChar.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaClass.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaDouble.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaField.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaFloat.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaHeapObject.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaHeapObjectVisitor.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaInt.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaLazyReadObject.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaLong.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaObject.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaObjectArray.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaObjectRef.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaShort.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaStatic.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaThing.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaValue.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaValueArray.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/ReachableExcludes.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/ReachableExcludesImpl.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/ReachableObjects.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/ReferenceChain.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/Root.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/Snapshot.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/StackFrame.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/StackTrace.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/oql/OQLEngine.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/oql/OQLException.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/oql/OQLQuery.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/oql/ObjectVisitor.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/parser/FileReadBuffer.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/parser/HprofReader.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/parser/MappedReadBuffer.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/parser/PositionDataInputStream.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/parser/PositionInputStream.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/parser/ReadBuffer.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/parser/Reader.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/AllClassesQuery.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/AllRootsQuery.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/ClassQuery.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/FinalizerObjectsQuery.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/FinalizerSummaryQuery.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/HistogramQuery.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/HttpReader.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/InstancesCountQuery.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/InstancesQuery.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/OQLHelp.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/OQLQuery.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/ObjectQuery.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/PlatformClasses.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/QueryHandler.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/QueryListener.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/ReachableQuery.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/RefsByTypeQuery.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/RootStackQuery.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/RootsQuery.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/util/ArraySorter.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/util/Comparer.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/util/CompositeEnumeration.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/util/Misc.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/util/VectorSorter.java
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/resources/hat.js
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/resources/oqlhelp.html
jdk/src/jdk.dev/share/classes/com/sun/tools/hat/resources/platform_names.txt
jdk/test/com/sun/management/HotSpotDiagnosticMXBean/DumpHeap.sh
jdk/test/sun/tools/common/ApplicationSetup.sh
jdk/test/sun/tools/common/CommonSetup.sh
jdk/test/sun/tools/common/ShutdownSimpleApplication.java
jdk/test/sun/tools/common/SimpleApplication.java
jdk/test/sun/tools/common/SleeperApplication.java
jdk/test/sun/tools/jhat/HatHeapDump1Test.java
jdk/test/sun/tools/jhat/HelloWorld.java
jdk/test/sun/tools/jhat/ParseTest.sh
jdk/test/sun/tools/jhat/README.TXT
--- a/.hgtags-top-repo	Thu May 21 10:07:37 2015 -0700
+++ b/.hgtags-top-repo	Wed Jul 05 20:35:10 2017 +0200
@@ -307,3 +307,4 @@
 105d045a69174d870b69bfe471b3f2d05a9f8ecc jdk9-b62
 0b32ed628fa60e4ab99fb0b5866d648e16231f17 jdk9-b63
 82cf9aab9a83e41c8194ba01af9666afdb856cbe jdk9-b64
+7c31f9d7b932f7924f1258d52885b1c7c3e078c2 jdk9-b65
--- a/common/bin/compare_exceptions.sh.incl	Thu May 21 10:07:37 2015 -0700
+++ b/common/bin/compare_exceptions.sh.incl	Wed Jul 05 20:35:10 2017 +0200
@@ -83,7 +83,6 @@
 ./bin/jcmd
 ./bin/jconsole
 ./bin/jdb
-./bin/jhat
 ./bin/jimage
 ./bin/jinfo
 ./bin/jjs
@@ -163,7 +162,6 @@
 ./bin/jcmd
 ./bin/jconsole
 ./bin/jdb
-./bin/jhat
 ./bin/jimage
 ./bin/jinfo
 ./bin/jjs
@@ -284,7 +282,6 @@
 ./bin/jcmd
 ./bin/jconsole
 ./bin/jdb
-./bin/jhat
 ./bin/jimage
 ./bin/jinfo
 ./bin/jjs
@@ -420,7 +417,6 @@
 ./bin/jcmd
 ./bin/jconsole
 ./bin/jdb
-./bin/jhat
 ./bin/jimage
 ./bin/jinfo
 ./bin/jjs
@@ -499,7 +495,6 @@
 ./bin/jcmd.exe
 ./bin/jconsole.exe
 ./bin/jdb.exe
-./bin/jhat.exe
 ./bin/jimage.exe
 ./bin/jinfo.exe
 ./bin/jjs.exe
@@ -579,7 +574,6 @@
 ./bin/jcmd
 ./bin/jconsole
 ./bin/jdb
-./bin/jhat
 ./bin/jimage
 ./bin/jinfo
 ./bin/jjs
--- a/corba/.hgtags	Thu May 21 10:07:37 2015 -0700
+++ b/corba/.hgtags	Wed Jul 05 20:35:10 2017 +0200
@@ -307,3 +307,4 @@
 d27f7e0a7aca129969de23e9934408a31b4abf4c jdk9-b62
 0acac6937de7a0868f8c6f88b7d036d780abeee6 jdk9-b63
 0a5e5a7c3539e8bde73d9fe55750e49a49cb8dac jdk9-b64
+afc1e295c4bf83f9a5dd539c29914edd4a754a3f jdk9-b65
--- a/hotspot/.hgignore	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/.hgignore	Wed Jul 05 20:35:10 2017 +0200
@@ -6,5 +6,7 @@
 ^src/share/tools/IdealGraphVisualizer/[a-zA-Z0-9]*/build/
 ^src/share/tools/IdealGraphVisualizer/build/
 ^src/share/tools/IdealGraphVisualizer/dist/
+^src/share/tools/IdealGraphVisualizer/nbplatform/
+.igv.log
 ^.hgtip
 .DS_Store
--- a/hotspot/.hgtags	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/.hgtags	Wed Jul 05 20:35:10 2017 +0200
@@ -467,3 +467,4 @@
 1eab877142cce6ca06e556e2ad0af688f993f00b jdk9-b62
 2ac9b6b36689b50d1562627067c92d51781b5684 jdk9-b63
 bf92b8db249cdfa5651ef954b6c0743a7e0ea4cd jdk9-b64
+e7ae94c4f35e940ea423fc1dd260435df34a77c0 jdk9-b65
--- a/hotspot/agent/src/share/classes/sun/jvm/hotspot/HSDB.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/agent/src/share/classes/sun/jvm/hotspot/HSDB.java	Wed Jul 05 20:35:10 2017 +0200
@@ -27,9 +27,7 @@
 import java.io.*;
 import java.awt.*;
 import java.awt.event.*;
-import java.math.*;
 import javax.swing.*;
-import javax.swing.tree.*;
 import java.util.*;
 
 import sun.jvm.hotspot.code.*;
@@ -928,7 +926,7 @@
             boolean shouldSkipOopMaps = false;
             if (curVFrame.isCompiledFrame()) {
               CodeBlob cb = VM.getVM().getCodeCache().findBlob(curFrame.getPC());
-              OopMapSet maps = cb.getOopMaps();
+              ImmutableOopMapSet maps = cb.getOopMaps();
               if ((maps == null) || (maps.getSize() == 0)) {
                 shouldSkipOopMaps = true;
               }
@@ -977,7 +975,7 @@
             } while (nextVFrame != null && nextFrame.equals(curFrame));
 
             if (shouldSkipOopMaps) {
-              anno = anno + "\nNOTE: null or empty OopMapSet found for this CodeBlob";
+              anno = anno + "\nNOTE: null or empty ImmutableOopMapSet found for this CodeBlob";
             }
 
             if (curFrame.getFP() != null) {
--- a/hotspot/agent/src/share/classes/sun/jvm/hotspot/code/CodeBlob.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/agent/src/share/classes/sun/jvm/hotspot/code/CodeBlob.java	Wed Jul 05 20:35:10 2017 +0200
@@ -171,17 +171,17 @@
   public boolean isLockedByVM()         { return false; }
 
   /** OopMap for frame; can return null if none available */
-  public OopMapSet getOopMaps() {
+  public ImmutableOopMapSet getOopMaps() {
     Address oopMapsAddr = oopMapsField.getValue(addr);
     if (oopMapsAddr == null) {
       return null;
     }
-    return new OopMapSet(oopMapsAddr);
+    return new ImmutableOopMapSet(oopMapsAddr);
   }
   // FIXME: not yet implementable
-  //  void set_oop_maps(OopMapSet* p);
+  //  void set_oop_maps(ImmutableOopMapSet* p);
 
-  public OopMap getOopMapForReturnAddress(Address returnAddress, boolean debugging) {
+  public ImmutableOopMap getOopMapForReturnAddress(Address returnAddress, boolean debugging) {
     Address pc = returnAddress;
     if (Assert.ASSERTS_ENABLED) {
       Assert.that(getOopMaps() != null, "nope");
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/agent/src/share/classes/sun/jvm/hotspot/compiler/ImmutableOopMap.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,67 @@
+/*
+ * Copyright (c) 2000, 2004, Oracle and/or its affiliates. All rights reserved.
+ * 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 sun.jvm.hotspot.compiler;
+
+import java.util.*;
+
+import sun.jvm.hotspot.code.*;
+import sun.jvm.hotspot.debugger.*;
+import sun.jvm.hotspot.runtime.*;
+import sun.jvm.hotspot.types.*;
+
+public class ImmutableOopMap extends VMObject {
+  private static CIntegerField countField;
+  private static long classSize;
+
+  static {
+    VM.registerVMInitializedObserver(new Observer() {
+        public void update(Observable o, Object data) {
+          initialize(VM.getVM().getTypeDataBase());
+        }
+      });
+  }
+
+  private static void initialize(TypeDataBase db) {
+    Type type = db.lookupType("ImmutableOopMap");
+    countField = type.getCIntegerField("_count");
+    classSize = type.getSize();
+  }
+
+  public ImmutableOopMap(Address addr) {
+    super(addr);
+  }
+
+  //--------------------------------------------------------------------------------
+  // Internals only below this point
+  //
+
+  long getCount() {
+    return countField.getValue(addr);
+  }
+
+  public Address getData() {
+    return addr.addOffsetTo(classSize);
+  }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/agent/src/share/classes/sun/jvm/hotspot/compiler/ImmutableOopMapPair.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,74 @@
+/*
+ * 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 sun.jvm.hotspot.compiler;
+
+import sun.jvm.hotspot.debugger.Address;
+import sun.jvm.hotspot.runtime.VM;
+import sun.jvm.hotspot.types.CIntegerField;
+import sun.jvm.hotspot.types.Type;
+import sun.jvm.hotspot.types.TypeDataBase;
+
+import java.util.Observable;
+import java.util.Observer;
+
+public class ImmutableOopMapPair {
+  private static CIntegerField pcField;
+  private static CIntegerField offsetField;
+  private static long classSize;
+
+  static {
+    VM.registerVMInitializedObserver(new Observer() {
+      public void update(Observable o, Object data) {
+        initialize(VM.getVM().getTypeDataBase());
+      }
+    });
+  }
+
+  private final Address address;
+
+  public ImmutableOopMapPair(Address address) {
+    this.address = address;
+  }
+
+  public static long classSize() {
+    return classSize;
+  }
+
+  public int getPC() {
+    return (int) pcField.getValue(address);
+  }
+
+  public int getOffset() {
+    return (int) offsetField.getValue(address);
+  }
+
+  private static void initialize(TypeDataBase db) {
+    Type type = db.lookupType("ImmutableOopMapPair");
+
+    pcField = type.getCIntegerField("_pc_offset");
+    offsetField = type.getCIntegerField("_oopmap_offset");
+    classSize = type.getSize();
+  }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/agent/src/share/classes/sun/jvm/hotspot/compiler/ImmutableOopMapSet.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,318 @@
+/*
+ * Copyright (c) 2000, 2008, Oracle and/or its affiliates. All rights reserved.
+ * 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 sun.jvm.hotspot.compiler;
+
+import java.util.*;
+
+import sun.jvm.hotspot.code.*;
+import sun.jvm.hotspot.debugger.*;
+import sun.jvm.hotspot.runtime.*;
+import sun.jvm.hotspot.types.*;
+import sun.jvm.hotspot.utilities.*;
+
+public class ImmutableOopMapSet extends VMObject {
+  private static final boolean DEBUG = System.getProperty("sun.jvm.hotspot.compiler.ImmutableOopMapSet.DEBUG") != null;
+
+  private static CIntegerField countField;
+  private static CIntegerField sizeField;
+  private static AddressField omDataField;
+  private static int REG_COUNT;
+  private static int SAVED_ON_ENTRY_REG_COUNT;
+  private static int C_SAVED_ON_ENTRY_REG_COUNT;
+  private static long classSize;
+
+  private static class MyVisitor implements OopMapVisitor {
+    private AddressVisitor addressVisitor;
+
+    public MyVisitor(AddressVisitor oopVisitor) {
+      setAddressVisitor(oopVisitor);
+    }
+
+    public void setAddressVisitor(AddressVisitor addressVisitor) {
+      this.addressVisitor = addressVisitor;
+    }
+
+    public void visitOopLocation(Address oopAddr) {
+      addressVisitor.visitAddress(oopAddr);
+    }
+
+    public void visitDerivedOopLocation(Address baseOopAddr, Address derivedOopAddr) {
+      if (VM.getVM().isClientCompiler()) {
+        Assert.that(false, "should not reach here");
+      } else if (VM.getVM().isServerCompiler() &&
+          VM.getVM().useDerivedPointerTable()) {
+        Assert.that(false, "FIXME: add derived pointer table");
+      }
+    }
+
+    public void visitValueLocation(Address valueAddr) {
+    }
+
+    public void visitNarrowOopLocation(Address narrowOopAddr) {
+      addressVisitor.visitCompOopAddress(narrowOopAddr);
+    }
+  }
+
+  static {
+    VM.registerVMInitializedObserver(new Observer() {
+      public void update(Observable o, Object data) {
+        initialize(VM.getVM().getTypeDataBase());
+      }
+    });
+  }
+
+  private static void initialize(TypeDataBase db) {
+    Type type = db.lookupType("ImmutableOopMapSet");
+
+    countField = type.getCIntegerField("_count");
+    sizeField = type.getCIntegerField("_size");
+    classSize = type.getSize();
+
+    if (!VM.getVM().isCore()) {
+      REG_COUNT = db.lookupIntConstant("REG_COUNT").intValue();
+      if (VM.getVM().isServerCompiler()) {
+        SAVED_ON_ENTRY_REG_COUNT = (int) db.lookupIntConstant("SAVED_ON_ENTRY_REG_COUNT").intValue();
+        C_SAVED_ON_ENTRY_REG_COUNT = (int) db.lookupIntConstant("C_SAVED_ON_ENTRY_REG_COUNT").intValue();
+      }
+    }
+  }
+
+  public ImmutableOopMapSet(Address addr) {
+    super(addr);
+  }
+
+  /**
+   * Returns the number of OopMaps in this ImmutableOopMapSet
+   */
+  public long getSize() {
+    return countField.getValue(addr);
+  }
+
+  public int getCount() { return (int) countField.getValue(addr); }
+
+  private Address dataStart() {
+    return (addr.addOffsetTo(ImmutableOopMapSet.classSize * getCount()));
+  }
+
+  public ImmutableOopMapPair pairAt(int index) {
+    Assert.that((index >= 0) && (index < getCount()), "bad index");
+    return new ImmutableOopMapPair(addr.addOffsetTo(index * ImmutableOopMapPair.classSize()));
+  }
+
+  /**
+   * returns the OopMap at a given index
+   */
+  public ImmutableOopMap getMapAt(int index) {
+    if (Assert.ASSERTS_ENABLED) {
+      Assert.that((index >= 0) && (index <= getSize()), "bad index");
+    }
+
+    ImmutableOopMapPair immutableOopMapPair = pairAt(index);
+    return getMap(immutableOopMapPair);
+  }
+
+  public ImmutableOopMap findMapAtOffset(long pcOffset, boolean debugging) {
+    int i;
+    int len = (int) getSize();
+    if (Assert.ASSERTS_ENABLED) {
+      Assert.that(len > 0, "must have pointer maps");
+    }
+
+    // Scan through oopmaps. Stop when current offset is either equal or greater
+    // than the one we are looking for.
+    for (i = 0; i < len; i++) {
+      if (pairAt(i).getPC() >= pcOffset) {
+        break;
+      }
+    }
+
+    if (!debugging) {
+      if (Assert.ASSERTS_ENABLED) {
+        Assert.that(i < len, "oopmap not found for pcOffset = " + pcOffset + "; len = " + len);
+        Assert.that(pairAt(i).getPC() == pcOffset, "oopmap not found");
+      }
+    } else {
+      if (i == len) {
+        if (DEBUG) {
+          System.out.println("can't find oopmap at " + pcOffset);
+          System.out.print("Oopmap offsets are [ ");
+          for (i = 0; i < len; i++) {
+            System.out.print(pairAt(i).getPC());
+          }
+          System.out.println("]");
+        }
+        i = len - 1;
+        return getMapAt(i);
+      }
+    }
+
+    ImmutableOopMap m = getMapAt(i);
+    return m;
+  }
+
+  /**
+   * Visitation -- iterates through the frame for a compiled method.
+   * This is a very generic mechanism that requires the Address to be
+   * dereferenced by the callee. Other, more specialized, visitation
+   * mechanisms are given below.
+   */
+  public static void oopsDo(Frame fr, CodeBlob cb, RegisterMap regMap, AddressVisitor oopVisitor, boolean debugging) {
+    allDo(fr, cb, regMap, new MyVisitor(oopVisitor), debugging);
+  }
+
+  /**
+   * Note that there are 4 required AddressVisitors: one for oops,
+   * one for derived oops, one for values, and one for dead values
+   */
+  public static void allDo(Frame fr, CodeBlob cb, RegisterMap regMap, OopMapVisitor visitor, boolean debugging) {
+    if (Assert.ASSERTS_ENABLED) {
+      CodeBlob tmpCB = VM.getVM().getCodeCache().findBlob(fr.getPC());
+      Assert.that(tmpCB != null && cb.equals(tmpCB), "wrong codeblob passed in");
+    }
+
+    ImmutableOopMapSet maps = cb.getOopMaps();
+    ImmutableOopMap map = cb.getOopMapForReturnAddress(fr.getPC(), debugging);
+    if (Assert.ASSERTS_ENABLED) {
+      Assert.that(map != null, "no ptr map found");
+    }
+
+    // handle derived pointers first (otherwise base pointer may be
+    // changed before derived pointer offset has been collected)
+    OopMapValue omv;
+    {
+      for (OopMapStream oms = new OopMapStream(map, OopMapValue.OopTypes.DERIVED_OOP_VALUE); !oms.isDone(); oms.next()) {
+        if (VM.getVM().isClientCompiler()) {
+          Assert.that(false, "should not reach here");
+        }
+        omv = oms.getCurrent();
+        Address loc = fr.oopMapRegToLocation(omv.getReg(), regMap);
+        if (loc != null) {
+          Address baseLoc = fr.oopMapRegToLocation(omv.getContentReg(), regMap);
+          Address derivedLoc = loc;
+          visitor.visitDerivedOopLocation(baseLoc, derivedLoc);
+        }
+      }
+    }
+
+    // We want narow oop, value and oop oop_types
+    OopMapValue.OopTypes[] values = new OopMapValue.OopTypes[]{
+        OopMapValue.OopTypes.OOP_VALUE, OopMapValue.OopTypes.VALUE_VALUE, OopMapValue.OopTypes.NARROWOOP_VALUE
+    };
+
+    {
+      for (OopMapStream oms = new OopMapStream(map, values); !oms.isDone(); oms.next()) {
+        omv = oms.getCurrent();
+        Address loc = fr.oopMapRegToLocation(omv.getReg(), regMap);
+        if (loc != null) {
+          if (omv.getType() == OopMapValue.OopTypes.OOP_VALUE) {
+            // This assert commented out because this will be useful
+            // to detect in the debugging system
+            // assert(Universe::is_heap_or_null(*loc), "found non oop pointer");
+            visitor.visitOopLocation(loc);
+          } else if (omv.getType() == OopMapValue.OopTypes.VALUE_VALUE) {
+            visitor.visitValueLocation(loc);
+          } else if (omv.getType() == OopMapValue.OopTypes.NARROWOOP_VALUE) {
+            visitor.visitNarrowOopLocation(loc);
+          }
+        }
+      }
+    }
+  }
+
+  /**
+   * Update callee-saved register info for the following frame.
+   * Should only be called in non-core builds.
+   */
+  public static void updateRegisterMap(Frame fr, CodeBlob cb, RegisterMap regMap, boolean debugging) {
+    if (Assert.ASSERTS_ENABLED) {
+      Assert.that(!VM.getVM().isCore(), "non-core builds only");
+    }
+
+    if (!VM.getVM().isDebugging()) {
+      if (Assert.ASSERTS_ENABLED) {
+        ImmutableOopMapSet maps = cb.getOopMaps();
+        Assert.that((maps != null) && (maps.getSize() > 0), "found null or empty ImmutableOopMapSet for CodeBlob");
+      }
+    } else {
+      // Hack for some topmost frames that have been found with empty
+      // OopMapSets. (Actually have not seen the null case, but don't
+      // want to take any chances.) See HSDB.showThreadStackMemory().
+      ImmutableOopMapSet maps = cb.getOopMaps();
+      if ((maps == null) || (maps.getSize() == 0)) {
+        return;
+      }
+    }
+
+    // Check if caller must update oop argument
+    regMap.setIncludeArgumentOops(cb.callerMustGCArguments());
+
+    int nofCallee = 0;
+    Address[] locs = new Address[2 * REG_COUNT + 1];
+    VMReg[] regs = new VMReg[2 * REG_COUNT + 1];
+    // ("+1" because REG_COUNT might be zero)
+
+    // Scan through oopmap and find location of all callee-saved registers
+    // (we do not do update in place, since info could be overwritten)
+    ImmutableOopMap map = cb.getOopMapForReturnAddress(fr.getPC(), debugging);
+    if (Assert.ASSERTS_ENABLED) {
+      Assert.that(map != null, "no ptr map found");
+    }
+
+    OopMapValue omv = null;
+    for (OopMapStream oms = new OopMapStream(map, OopMapValue.OopTypes.CALLEE_SAVED_VALUE); !oms.isDone(); oms.next()) {
+      omv = oms.getCurrent();
+      if (Assert.ASSERTS_ENABLED) {
+        Assert.that(nofCallee < 2 * REG_COUNT, "overflow");
+      }
+      regs[nofCallee] = omv.getContentReg();
+      locs[nofCallee] = fr.oopMapRegToLocation(omv.getReg(), regMap);
+      nofCallee++;
+    }
+
+    // Check that runtime stubs save all callee-saved registers
+    // After adapter frames were deleted C2 doesn't use callee save registers at present
+    if (Assert.ASSERTS_ENABLED) {
+      if (VM.getVM().isServerCompiler()) {
+        Assert.that(!cb.isRuntimeStub() ||
+                (nofCallee >= SAVED_ON_ENTRY_REG_COUNT || nofCallee >= C_SAVED_ON_ENTRY_REG_COUNT),
+            "must save all");
+      }
+    }
+
+    // Copy found callee-saved register to reg_map
+    for (int i = 0; i < nofCallee; i++) {
+      regMap.setLocation(regs[i], locs[i]);
+    }
+  }
+
+  public ImmutableOopMapPair getPairAt(int index) {
+    return pairAt(index);
+  }
+
+  public ImmutableOopMap getMap(ImmutableOopMapPair pair) {
+    Assert.that(pair.getOffset() < (int) sizeField.getValue(), "boundary check");
+    return new ImmutableOopMap(dataStart().addOffsetTo(pair.getOffset()));
+  }
+}
--- a/hotspot/agent/src/share/classes/sun/jvm/hotspot/compiler/OopMap.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,101 +0,0 @@
-/*
- * Copyright (c) 2000, 2004, Oracle and/or its affiliates. All rights reserved.
- * 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 sun.jvm.hotspot.compiler;
-
-import java.util.*;
-
-import sun.jvm.hotspot.code.*;
-import sun.jvm.hotspot.debugger.*;
-import sun.jvm.hotspot.runtime.*;
-import sun.jvm.hotspot.types.*;
-
-public class OopMap extends VMObject {
-  private static CIntegerField pcOffsetField;
-  private static CIntegerField omvCountField;
-  private static CIntegerField omvDataSizeField;
-  private static AddressField  omvDataField;
-  private static AddressField  compressedWriteStreamField;
-
-  // This is actually a field inside class CompressedStream
-  private static AddressField  compressedStreamBufferField;
-
-  static {
-    VM.registerVMInitializedObserver(new Observer() {
-        public void update(Observable o, Object data) {
-          initialize(VM.getVM().getTypeDataBase());
-        }
-      });
-  }
-
-  private static void initialize(TypeDataBase db) {
-    Type type = db.lookupType("OopMap");
-
-    pcOffsetField              = type.getCIntegerField("_pc_offset");
-    omvCountField              = type.getCIntegerField("_omv_count");
-    omvDataSizeField           = type.getCIntegerField("_omv_data_size");
-    omvDataField               = type.getAddressField("_omv_data");
-    compressedWriteStreamField = type.getAddressField("_write_stream");
-
-    type = db.lookupType("CompressedStream");
-    compressedStreamBufferField = type.getAddressField("_buffer");
-  }
-
-  public OopMap(Address addr) {
-    super(addr);
-  }
-
-  public long getOffset() {
-    return pcOffsetField.getValue(addr);
-  }
-
-  //--------------------------------------------------------------------------------
-  // Internals only below this point
-  //
-
-  // Accessors -- package private for now
-  Address getOMVData() {
-    return omvDataField.getValue(addr);
-  }
-
-  long getOMVDataSize() {
-    return omvDataSizeField.getValue(addr);
-  }
-
-  long getOMVCount() {
-    return omvCountField.getValue(addr);
-  }
-
-  CompressedWriteStream getWriteStream() {
-    Address wsAddr = compressedWriteStreamField.getValue(addr);
-    if (wsAddr == null) {
-      return null;
-    }
-    Address bufferAddr = compressedStreamBufferField.getValue(wsAddr);
-    if (bufferAddr == null) {
-      return null;
-    }
-    return new CompressedWriteStream(bufferAddr);
-  }
-}
--- a/hotspot/agent/src/share/classes/sun/jvm/hotspot/compiler/OopMapSet.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,289 +0,0 @@
-/*
- * Copyright (c) 2000, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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 sun.jvm.hotspot.compiler;
-
-import java.util.*;
-
-import sun.jvm.hotspot.code.*;
-import sun.jvm.hotspot.debugger.*;
-import sun.jvm.hotspot.runtime.*;
-import sun.jvm.hotspot.types.*;
-import sun.jvm.hotspot.utilities.*;
-
-public class OopMapSet extends VMObject {
-  private static final boolean DEBUG = System.getProperty("sun.jvm.hotspot.compiler.OopMapSet.DEBUG") != null;
-
-  private static CIntegerField omCountField;
-  private static CIntegerField omSizeField;
-  private static AddressField  omDataField;
-  private static int REG_COUNT;
-  private static int SAVED_ON_ENTRY_REG_COUNT;
-  private static int C_SAVED_ON_ENTRY_REG_COUNT;
-  private static class MyVisitor implements OopMapVisitor {
-    private AddressVisitor addressVisitor;
-
-    public MyVisitor(AddressVisitor oopVisitor) {
-      setAddressVisitor(oopVisitor);
-    }
-
-    public void setAddressVisitor(AddressVisitor addressVisitor) {
-      this.addressVisitor = addressVisitor;
-    }
-
-    public void visitOopLocation(Address oopAddr) {
-      addressVisitor.visitAddress(oopAddr);
-    }
-
-    public void visitDerivedOopLocation(Address baseOopAddr, Address derivedOopAddr) {
-      if (VM.getVM().isClientCompiler()) {
-        Assert.that(false, "should not reach here");
-      } else if (VM.getVM().isServerCompiler() &&
-                 VM.getVM().useDerivedPointerTable()) {
-        Assert.that(false, "FIXME: add derived pointer table");
-      }
-    }
-
-    public void visitValueLocation(Address valueAddr) {
-    }
-
-    public void visitNarrowOopLocation(Address narrowOopAddr) {
-      addressVisitor.visitCompOopAddress(narrowOopAddr);
-    }
-  }
-
-  static {
-    VM.registerVMInitializedObserver(new Observer() {
-        public void update(Observable o, Object data) {
-          initialize(VM.getVM().getTypeDataBase());
-        }
-      });
-  }
-
-  private static void initialize(TypeDataBase db) {
-    Type type = db.lookupType("OopMapSet");
-
-    omCountField  = type.getCIntegerField("_om_count");
-    omSizeField   = type.getCIntegerField("_om_size");
-    omDataField   = type.getAddressField("_om_data");
-
-    if (!VM.getVM().isCore()) {
-      REG_COUNT = db.lookupIntConstant("REG_COUNT").intValue();
-      if (VM.getVM().isServerCompiler()) {
-        SAVED_ON_ENTRY_REG_COUNT = (int) db.lookupIntConstant("SAVED_ON_ENTRY_REG_COUNT").intValue();
-        C_SAVED_ON_ENTRY_REG_COUNT = (int) db.lookupIntConstant("C_SAVED_ON_ENTRY_REG_COUNT").intValue();
-      }
-    }
-  }
-
-  public OopMapSet(Address addr) {
-    super(addr);
-  }
-
-  /** Returns the number of OopMaps in this OopMapSet */
-  public long getSize() {
-    return omCountField.getValue(addr);
-  }
-
-  /** returns the OopMap at a given index */
-  public OopMap getMapAt(int index) {
-    if (Assert.ASSERTS_ENABLED) {
-      Assert.that((index >= 0) && (index <= getSize()),"bad index");
-    }
-    Address omDataAddr = omDataField.getValue(addr);
-    Address oopMapAddr = omDataAddr.getAddressAt(index * VM.getVM().getAddressSize());
-    if (oopMapAddr == null) {
-      return null;
-    }
-    return new OopMap(oopMapAddr);
-  }
-
-  public OopMap findMapAtOffset(long pcOffset, boolean debugging) {
-    int i;
-    int len = (int) getSize();
-    if (Assert.ASSERTS_ENABLED) {
-      Assert.that(len > 0, "must have pointer maps");
-    }
-
-    // Scan through oopmaps. Stop when current offset is either equal or greater
-    // than the one we are looking for.
-    for (i = 0; i < len; i++) {
-      if (getMapAt(i).getOffset() >= pcOffset) {
-        break;
-      }
-    }
-
-    if (!debugging) {
-      if (Assert.ASSERTS_ENABLED) {
-        Assert.that(i < len, "oopmap not found for pcOffset = " + pcOffset + "; len = " + len);
-        Assert.that(getMapAt(i).getOffset() == pcOffset, "oopmap not found");
-      }
-    } else {
-      if (i == len) {
-        if (DEBUG) {
-          System.out.println("can't find oopmap at " + pcOffset);
-          System.out.print("Oopmap offsets are [ ");
-          for (i = 0; i < len; i++) {
-            System.out.print(getMapAt(i).getOffset());
-          }
-          System.out.println("]");
-        }
-        i = len - 1;
-        return getMapAt(i);
-      }
-    }
-
-    OopMap m = getMapAt(i);
-    return m;
-  }
-
-  /** Visitation -- iterates through the frame for a compiled method.
-      This is a very generic mechanism that requires the Address to be
-      dereferenced by the callee. Other, more specialized, visitation
-      mechanisms are given below. */
-  public static void oopsDo(Frame fr, CodeBlob cb, RegisterMap regMap, AddressVisitor oopVisitor, boolean debugging) {
-    allDo(fr, cb, regMap, new MyVisitor(oopVisitor), debugging);
-  }
-
-  /** Note that there are 4 required AddressVisitors: one for oops,
-      one for derived oops, one for values, and one for dead values */
-  public static void allDo(Frame fr, CodeBlob cb, RegisterMap regMap, OopMapVisitor visitor, boolean debugging) {
-    if (Assert.ASSERTS_ENABLED) {
-      CodeBlob tmpCB = VM.getVM().getCodeCache().findBlob(fr.getPC());
-      Assert.that(tmpCB != null && cb.equals(tmpCB), "wrong codeblob passed in");
-    }
-
-    OopMapSet maps = cb.getOopMaps();
-    OopMap map = cb.getOopMapForReturnAddress(fr.getPC(), debugging);
-    if (Assert.ASSERTS_ENABLED) {
-      Assert.that(map != null, "no ptr map found");
-    }
-
-    // handle derived pointers first (otherwise base pointer may be
-    // changed before derived pointer offset has been collected)
-    OopMapValue omv;
-    {
-      for (OopMapStream oms = new OopMapStream(map, OopMapValue.OopTypes.DERIVED_OOP_VALUE); !oms.isDone(); oms.next()) {
-        if (VM.getVM().isClientCompiler()) {
-          Assert.that(false, "should not reach here");
-        }
-        omv = oms.getCurrent();
-        Address loc = fr.oopMapRegToLocation(omv.getReg(), regMap);
-        if (loc != null) {
-          Address baseLoc    = fr.oopMapRegToLocation(omv.getContentReg(), regMap);
-          Address derivedLoc = loc;
-          visitor.visitDerivedOopLocation(baseLoc, derivedLoc);
-        }
-      }
-    }
-
-    // We want narow oop, value and oop oop_types
-    OopMapValue.OopTypes[] values = new OopMapValue.OopTypes[] {
-      OopMapValue.OopTypes.OOP_VALUE, OopMapValue.OopTypes.VALUE_VALUE, OopMapValue.OopTypes.NARROWOOP_VALUE
-    };
-
-    {
-      for (OopMapStream oms = new OopMapStream(map, values); !oms.isDone(); oms.next()) {
-        omv = oms.getCurrent();
-        Address loc = fr.oopMapRegToLocation(omv.getReg(), regMap);
-        if (loc != null) {
-          if (omv.getType() == OopMapValue.OopTypes.OOP_VALUE) {
-            // This assert commented out because this will be useful
-            // to detect in the debugging system
-            // assert(Universe::is_heap_or_null(*loc), "found non oop pointer");
-            visitor.visitOopLocation(loc);
-          } else if (omv.getType() == OopMapValue.OopTypes.VALUE_VALUE) {
-            visitor.visitValueLocation(loc);
-          } else if (omv.getType() == OopMapValue.OopTypes.NARROWOOP_VALUE) {
-            visitor.visitNarrowOopLocation(loc);
-          }
-        }
-      }
-    }
-  }
-
-  /** Update callee-saved register info for the following frame.
-      Should only be called in non-core builds. */
-  public static void updateRegisterMap(Frame fr, CodeBlob cb, RegisterMap regMap, boolean debugging) {
-    if (Assert.ASSERTS_ENABLED) {
-      Assert.that(!VM.getVM().isCore(), "non-core builds only");
-    }
-
-    if (!VM.getVM().isDebugging()) {
-      if (Assert.ASSERTS_ENABLED) {
-        OopMapSet maps = cb.getOopMaps();
-        Assert.that((maps != null) && (maps.getSize() > 0), "found null or empty OopMapSet for CodeBlob");
-      }
-    } else {
-      // Hack for some topmost frames that have been found with empty
-      // OopMapSets. (Actually have not seen the null case, but don't
-      // want to take any chances.) See HSDB.showThreadStackMemory().
-      OopMapSet maps = cb.getOopMaps();
-      if ((maps == null) || (maps.getSize() == 0)) {
-        return;
-      }
-    }
-
-    // Check if caller must update oop argument
-    regMap.setIncludeArgumentOops(cb.callerMustGCArguments());
-
-    int nofCallee = 0;
-    Address[] locs = new Address[2 * REG_COUNT + 1];
-    VMReg  [] regs = new VMReg  [2 * REG_COUNT + 1];
-    // ("+1" because REG_COUNT might be zero)
-
-    // Scan through oopmap and find location of all callee-saved registers
-    // (we do not do update in place, since info could be overwritten)
-    OopMap map  = cb.getOopMapForReturnAddress(fr.getPC(), debugging);
-    if (Assert.ASSERTS_ENABLED) {
-      Assert.that(map != null, "no ptr map found");
-    }
-
-    OopMapValue omv = null;
-    for(OopMapStream oms = new OopMapStream(map, OopMapValue.OopTypes.CALLEE_SAVED_VALUE); !oms.isDone(); oms.next()) {
-      omv = oms.getCurrent();
-      if (Assert.ASSERTS_ENABLED) {
-        Assert.that(nofCallee < 2 * REG_COUNT, "overflow");
-      }
-      regs[nofCallee] = omv.getContentReg();
-      locs[nofCallee] = fr.oopMapRegToLocation(omv.getReg(), regMap);
-      nofCallee++;
-    }
-
-    // Check that runtime stubs save all callee-saved registers
-    // After adapter frames were deleted C2 doesn't use callee save registers at present
-    if (Assert.ASSERTS_ENABLED) {
-      if (VM.getVM().isServerCompiler()) {
-        Assert.that(!cb.isRuntimeStub() ||
-                    (nofCallee >= SAVED_ON_ENTRY_REG_COUNT || nofCallee >= C_SAVED_ON_ENTRY_REG_COUNT),
-                    "must save all");
-      }
-    }
-
-    // Copy found callee-saved register to reg_map
-    for (int i = 0; i < nofCallee; i++) {
-      regMap.setLocation(regs[i], locs[i]);
-    }
-  }
-}
--- a/hotspot/agent/src/share/classes/sun/jvm/hotspot/compiler/OopMapStream.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/agent/src/share/classes/sun/jvm/hotspot/compiler/OopMapStream.java	Wed Jul 05 20:35:10 2017 +0200
@@ -28,30 +28,26 @@
 
 public class OopMapStream {
   private CompressedReadStream stream;
-  private OopMap oopMap;
+  private ImmutableOopMap oopMap;
   private int mask;
   private int size;
   private int position;
   private OopMapValue omv;
   private boolean omvValid;
 
-  public OopMapStream(OopMap oopMap) {
+  public OopMapStream(ImmutableOopMap oopMap) {
     this(oopMap, (OopMapValue.OopTypes[]) null);
   }
 
-  public OopMapStream(OopMap oopMap, OopMapValue.OopTypes type) {
+  public OopMapStream(ImmutableOopMap oopMap, OopMapValue.OopTypes type) {
     this(oopMap, (OopMapValue.OopTypes[]) null);
     mask = type.getValue();
   }
 
-  public OopMapStream(OopMap oopMap, OopMapValue.OopTypes[] types) {
-    if (oopMap.getOMVData() == null) {
-      stream = new CompressedReadStream(oopMap.getWriteStream().getBuffer());
-    } else {
-      stream = new CompressedReadStream(oopMap.getOMVData());
-    }
+  public OopMapStream(ImmutableOopMap oopMap, OopMapValue.OopTypes[] types) {
+    stream = new CompressedReadStream(oopMap.getData());
     mask = computeMask(types);
-    size = (int) oopMap.getOMVCount();
+    size = (int) oopMap.getCount();
     position = 0;
     omv = new OopMapValue();
     omvValid = false;
--- a/hotspot/agent/src/share/classes/sun/jvm/hotspot/runtime/Frame.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/agent/src/share/classes/sun/jvm/hotspot/runtime/Frame.java	Wed Jul 05 20:35:10 2017 +0200
@@ -26,14 +26,12 @@
 
 import java.io.*;
 import java.util.*;
-import sun.jvm.hotspot.*;
+
 import sun.jvm.hotspot.code.*;
 import sun.jvm.hotspot.compiler.*;
-import sun.jvm.hotspot.c1.*;
 import sun.jvm.hotspot.debugger.*;
 import sun.jvm.hotspot.interpreter.*;
 import sun.jvm.hotspot.oops.*;
-import sun.jvm.hotspot.runtime.sparc.SPARCFrame;
 import sun.jvm.hotspot.types.*;
 import sun.jvm.hotspot.utilities.*;
 
@@ -626,7 +624,7 @@
       Assert.that(cb != null, "sanity check");
     }
     if (cb.getOopMaps() != null) {
-      OopMapSet.oopsDo(this, cb, regMap, oopVisitor, VM.getVM().isDebugging());
+      ImmutableOopMapSet.oopsDo(this, cb, regMap, oopVisitor, VM.getVM().isDebugging());
 
       // FIXME: add in traversal of argument oops (skipping this for
       // now until we have the other stuff tested)
--- a/hotspot/agent/src/share/classes/sun/jvm/hotspot/runtime/ppc64/PPC64Frame.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/agent/src/share/classes/sun/jvm/hotspot/runtime/ppc64/PPC64Frame.java	Wed Jul 05 20:35:10 2017 +0200
@@ -358,7 +358,7 @@
       map.setIncludeArgumentOops(cb.callerMustGCArguments());
 
       if (cb.getOopMaps() != null) {
-        OopMapSet.updateRegisterMap(this, cb, map, true);
+        ImmutableOopMapSet.updateRegisterMap(this, cb, map, true);
       }
     }
 
--- a/hotspot/agent/src/share/classes/sun/jvm/hotspot/runtime/sparc/SPARCFrame.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/agent/src/share/classes/sun/jvm/hotspot/runtime/sparc/SPARCFrame.java	Wed Jul 05 20:35:10 2017 +0200
@@ -24,8 +24,6 @@
 
 package sun.jvm.hotspot.runtime.sparc;
 
-import java.util.*;
-
 import sun.jvm.hotspot.asm.sparc.*;
 import sun.jvm.hotspot.code.*;
 import sun.jvm.hotspot.compiler.*;
@@ -34,7 +32,6 @@
 import sun.jvm.hotspot.oops.*;
 import sun.jvm.hotspot.runtime.*;
 import sun.jvm.hotspot.runtime.posix.*;
-import sun.jvm.hotspot.types.*;
 import sun.jvm.hotspot.utilities.*;
 
 /** Specialization of and implementation of abstract methods of the
@@ -592,7 +589,7 @@
             map.setIncludeArgumentOops(true);
           }
           if (cb.getOopMaps() != null) {
-            OopMapSet.updateRegisterMap(this, cb, map, VM.getVM().isDebugging());
+            ImmutableOopMapSet.updateRegisterMap(this, cb, map, VM.getVM().isDebugging());
           }
         }
       }
--- a/hotspot/agent/src/share/classes/sun/jvm/hotspot/runtime/x86/X86Frame.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/agent/src/share/classes/sun/jvm/hotspot/runtime/x86/X86Frame.java	Wed Jul 05 20:35:10 2017 +0200
@@ -385,7 +385,7 @@
       map.setIncludeArgumentOops(cb.callerMustGCArguments());
 
       if (cb.getOopMaps() != null) {
-        OopMapSet.updateRegisterMap(this, cb, map, true);
+        ImmutableOopMapSet.updateRegisterMap(this, cb, map, true);
       }
 
       // Since the prolog does the save and restore of EBP there is no oopmap
--- a/hotspot/agent/src/share/classes/sun/jvm/hotspot/ui/classbrowser/HTMLGenerator.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/agent/src/share/classes/sun/jvm/hotspot/ui/classbrowser/HTMLGenerator.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,11 +31,9 @@
 import sun.jvm.hotspot.compiler.*;
 import sun.jvm.hotspot.debugger.*;
 import sun.jvm.hotspot.interpreter.*;
-import sun.jvm.hotspot.memory.*;
 import sun.jvm.hotspot.oops.*;
 import sun.jvm.hotspot.runtime.*;
 import sun.jvm.hotspot.tools.jcore.*;
-import sun.jvm.hotspot.types.*;
 import sun.jvm.hotspot.utilities.*;
 
 public class HTMLGenerator implements /* imports */ ClassConstants {
@@ -887,7 +885,7 @@
       private Formatter buf;
       private SymbolFinder symFinder = createSymbolFinder();
       private long pc;
-      private OopMapSet oms;
+      private ImmutableOopMapSet oms;
       private CodeBlob blob;
       private NMethod nmethod;
 
@@ -954,13 +952,13 @@
 
          if (oms != null) {
             long base = addressToLong(blob.codeBegin());
-            for (int i = 0, imax = (int)oms.getSize(); i < imax; i++) {
-               OopMap om = oms.getMapAt(i);
-               long omspc = base + om.getOffset();
+            for (int i = 0, imax = oms.getCount(); i < imax; i++) {
+               ImmutableOopMapPair pair = oms.getPairAt(i);
+               long omspc = base + pair.getPC();
                if (omspc > pc) {
                   if (omspc <= endPc) {
                      buf.br();
-                     buf.append(genOopMapInfo(om));
+                     buf.append(genOopMapInfo(oms.getMap(pair)));
                      // st.move_to(column);
                      // visitor.print("; ");
                         // om.print_on(st);
@@ -1167,7 +1165,7 @@
         }
     }
 
-   protected String genHTMLForOopMap(OopMap map) {
+   protected String genHTMLForOopMap(ImmutableOopMap map) {
       final int stack0 = VMRegImpl.getStack0().getValue();
       Formatter buf = new Formatter(genHTML);
 
@@ -1237,11 +1235,11 @@
 
 
    protected String genOopMapInfo(NMethod nmethod, PCDesc pcDesc) {
-      OopMapSet mapSet = nmethod.getOopMaps();
+      ImmutableOopMapSet mapSet = nmethod.getOopMaps();
       if (mapSet == null || (mapSet.getSize() <= 0))
         return "";
       int pcOffset = pcDesc.getPCOffset();
-      OopMap map = mapSet.findMapAtOffset(pcOffset, VM.getVM().isDebugging());
+      ImmutableOopMap map = mapSet.findMapAtOffset(pcOffset, VM.getVM().isDebugging());
       if (map == null) {
          throw new IllegalArgumentException("no oopmap at safepoint!");
       }
@@ -1249,7 +1247,7 @@
       return genOopMapInfo(map);
    }
 
-   protected String genOopMapInfo(OopMap map) {
+   protected String genOopMapInfo(ImmutableOopMap map) {
      Formatter buf = new Formatter(genHTML);
      buf.beginTag("pre");
      buf.append("OopMap: ");
--- a/hotspot/src/cpu/aarch64/vm/aarch64.ad	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/aarch64/vm/aarch64.ad	Wed Jul 05 20:35:10 2017 +0200
@@ -421,7 +421,40 @@
 );
 
 // Class for all non-special integer registers
-reg_class no_special_reg32(
+reg_class no_special_reg32_no_fp(
+    R0,
+    R1,
+    R2,
+    R3,
+    R4,
+    R5,
+    R6,
+    R7,
+    R10,
+    R11,
+    R12,                        // rmethod
+    R13,
+    R14,
+    R15,
+    R16,
+    R17,
+    R18,
+    R19,
+    R20,
+    R21,
+    R22,
+    R23,
+    R24,
+    R25,
+    R26
+ /* R27, */                     // heapbase
+ /* R28, */                     // thread
+ /* R29, */                     // fp
+ /* R30, */                     // lr
+ /* R31 */                      // sp
+);
+
+reg_class no_special_reg32_with_fp(
     R0,
     R1,
     R2,
@@ -454,8 +487,43 @@
  /* R31 */                      // sp
 );
 
+reg_class_dynamic no_special_reg32(no_special_reg32_no_fp, no_special_reg32_with_fp, %{ PreserveFramePointer %});
+
 // Class for all non-special long integer registers
-reg_class no_special_reg(
+reg_class no_special_reg_no_fp(
+    R0, R0_H,
+    R1, R1_H,
+    R2, R2_H,
+    R3, R3_H,
+    R4, R4_H,
+    R5, R5_H,
+    R6, R6_H,
+    R7, R7_H,
+    R10, R10_H,
+    R11, R11_H,
+    R12, R12_H,                 // rmethod
+    R13, R13_H,
+    R14, R14_H,
+    R15, R15_H,
+    R16, R16_H,
+    R17, R17_H,
+    R18, R18_H,
+    R19, R19_H,
+    R20, R20_H,
+    R21, R21_H,
+    R22, R22_H,
+    R23, R23_H,
+    R24, R24_H,
+    R25, R25_H,
+    R26, R26_H,
+ /* R27, R27_H, */              // heapbase
+ /* R28, R28_H, */              // thread
+ /* R29, R29_H, */              // fp
+ /* R30, R30_H, */              // lr
+ /* R31, R31_H */               // sp
+);
+
+reg_class no_special_reg_with_fp(
     R0, R0_H,
     R1, R1_H,
     R2, R2_H,
@@ -488,6 +556,8 @@
  /* R31, R31_H */               // sp
 );
 
+reg_class_dynamic no_special_reg(no_special_reg_no_fp, no_special_reg_with_fp, %{ PreserveFramePointer %});
+
 // Class for 64 bit register r0
 reg_class r0_reg(
     R0, R0_H
@@ -1637,12 +1707,7 @@
 int MachCallStaticJavaNode::ret_addr_offset()
 {
   // call should be a simple bl
-  // unless this is a method handle invoke in which case it is
-  // mov(rfp, sp), bl, mov(sp, rfp)
   int off = 4;
-  if (_method_handle_invoke) {
-    off += 4;
-  }
   return off;
 }
 
@@ -1753,14 +1818,13 @@
   if (C->need_stack_bang(framesize))
     st->print("# stack bang size=%d\n\t", framesize);
 
-  if (framesize == 0) {
-    // Is this even possible?
-    st->print("stp  lr, rfp, [sp, #%d]!", -(2 * wordSize));
-  } else if (framesize < ((1 << 9) + 2 * wordSize)) {
+  if (framesize < ((1 << 9) + 2 * wordSize)) {
     st->print("sub  sp, sp, #%d\n\t", framesize);
     st->print("stp  rfp, lr, [sp, #%d]", framesize - 2 * wordSize);
+    if (PreserveFramePointer) st->print("\n\tadd  rfp, sp, #%d", framesize - 2 * wordSize);
   } else {
     st->print("stp  lr, rfp, [sp, #%d]!\n\t", -(2 * wordSize));
+    if (PreserveFramePointer) st->print("mov  rfp, sp\n\t");
     st->print("mov  rscratch1, #%d\n\t", framesize - 2 * wordSize);
     st->print("sub  sp, sp, rscratch1");
   }
@@ -3517,34 +3581,6 @@
     }
   %}
 
-  enc_class aarch64_enc_java_handle_call(method meth) %{
-    MacroAssembler _masm(&cbuf);
-    relocInfo::relocType reloc;
-
-    // RFP is preserved across all calls, even compiled calls.
-    // Use it to preserve SP.
-    __ mov(rfp, sp);
-
-    const int start_offset = __ offset();
-    address addr = (address)$meth$$method;
-    if (!_method) {
-      // A call to a runtime wrapper, e.g. new, new_typeArray_Java, uncommon_trap.
-      __ trampoline_call(Address(addr, relocInfo::runtime_call_type), &cbuf);
-    } else if (_optimized_virtual) {
-      __ trampoline_call(Address(addr, relocInfo::opt_virtual_call_type), &cbuf);
-    } else {
-      __ trampoline_call(Address(addr, relocInfo::static_call_type), &cbuf);
-    }
-
-    if (_method) {
-      // Emit stub for static call
-      CompiledStaticCall::emit_to_interp_stub(cbuf);
-    }
-
-    // now restore sp
-    __ mov(sp, rfp);
-  %}
-
   enc_class aarch64_enc_java_dynamic_call(method meth) %{
     MacroAssembler _masm(&cbuf);
     __ ic_call((address)$meth$$method);
@@ -12561,8 +12597,6 @@
 
   effect(USE meth);
 
-  predicate(!((CallStaticJavaNode*)n)->is_method_handle_invoke());
-
   ins_cost(CALL_COST);
 
   format %{ "call,static $meth \t// ==> " %}
@@ -12575,26 +12609,6 @@
 
 // TO HERE
 
-// Call Java Static Instruction (method handle version)
-
-instruct CallStaticJavaDirectHandle(method meth, iRegP_FP reg_mh_save)
-%{
-  match(CallStaticJava);
-
-  effect(USE meth);
-
-  predicate(((CallStaticJavaNode*)n)->is_method_handle_invoke());
-
-  ins_cost(CALL_COST);
-
-  format %{ "call,static $meth \t// (methodhandle) ==> " %}
-
-  ins_encode( aarch64_enc_java_handle_call(meth),
-              aarch64_enc_call_epilog );
-
-  ins_pipe(pipe_class_call);
-%}
-
 // Call Java Dynamic Instruction
 instruct CallDynamicJavaDirect(method meth)
 %{
--- a/hotspot/src/cpu/aarch64/vm/c1_FrameMap_aarch64.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/aarch64/vm/c1_FrameMap_aarch64.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -346,8 +346,7 @@
 
 // JSR 292
 LIR_Opr FrameMap::method_handle_invoke_SP_save_opr() {
-  // assert(rfp == rbp_mh_SP_save, "must be same register");
-  return rfp_opr;
+  return LIR_OprFact::illegalOpr;  // Not needed on aarch64
 }
 
 
--- a/hotspot/src/cpu/aarch64/vm/c1_Runtime1_aarch64.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/aarch64/vm/c1_Runtime1_aarch64.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -443,18 +443,8 @@
     restore_live_registers(sasm, id != handle_exception_nofpu_id);
     break;
   case handle_exception_from_callee_id:
-    // Pop the return address since we are possibly changing SP (restoring from BP).
+    // Pop the return address.
     __ leave();
-
-    // Restore SP from FP if the exception PC is a method handle call site.
-    {
-      Label nope;
-      __ ldrw(rscratch1, Address(rthread, JavaThread::is_method_handle_return_offset()));
-      __ cbzw(rscratch1, nope);
-      __ mov(sp, rfp);
-      __ bind(nope);
-    }
-
     __ ret(lr);  // jump to exception handler
     break;
   default:  ShouldNotReachHere();
@@ -514,14 +504,6 @@
 
   __ verify_not_null_oop(exception_oop);
 
-  {
-    Label foo;
-    __ ldrw(rscratch1, Address(rthread, JavaThread::is_method_handle_return_offset()));
-    __ cbzw(rscratch1, foo);
-    __ mov(sp, rfp);
-    __ bind(foo);
-  }
-
   // continue at exception handler (return address removed)
   // note: do *not* remove arguments when unwinding the
   //       activation since the caller assumes having
--- a/hotspot/src/cpu/aarch64/vm/frame_aarch64.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/aarch64/vm/frame_aarch64.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -223,7 +223,8 @@
     if (sender_blob->is_nmethod()) {
         nmethod* nm = sender_blob->as_nmethod_or_null();
         if (nm != NULL) {
-            if (nm->is_deopt_mh_entry(sender_pc) || nm->is_deopt_entry(sender_pc)) {
+            if (nm->is_deopt_mh_entry(sender_pc) || nm->is_deopt_entry(sender_pc) ||
+                nm->method()->is_method_handle_intrinsic()) {
                 return false;
             }
         }
@@ -389,10 +390,9 @@
 // frame::verify_deopt_original_pc
 //
 // Verifies the calculated original PC of a deoptimization PC for the
-// given unextended SP.  The unextended SP might also be the saved SP
-// for MethodHandle call sites.
+// given unextended SP.
 #ifdef ASSERT
-void frame::verify_deopt_original_pc(nmethod* nm, intptr_t* unextended_sp, bool is_method_handle_return) {
+void frame::verify_deopt_original_pc(nmethod* nm, intptr_t* unextended_sp) {
   frame fr;
 
   // This is ugly but it's better than to change {get,set}_original_pc
@@ -402,33 +402,23 @@
 
   address original_pc = nm->get_original_pc(&fr);
   assert(nm->insts_contains(original_pc), "original PC must be in nmethod");
-  assert(nm->is_method_handle_return(original_pc) == is_method_handle_return, "must be");
 }
 #endif
 
 //------------------------------------------------------------------------------
 // frame::adjust_unextended_sp
 void frame::adjust_unextended_sp() {
-  // If we are returning to a compiled MethodHandle call site, the
-  // saved_fp will in fact be a saved value of the unextended SP.  The
-  // simplest way to tell whether we are returning to such a call site
-  // is as follows:
+  // On aarch64, sites calling method handle intrinsics and lambda forms are treated
+  // as any other call site. Therefore, no special action is needed when we are
+  // returning to any of these call sites.
 
   nmethod* sender_nm = (_cb == NULL) ? NULL : _cb->as_nmethod_or_null();
   if (sender_nm != NULL) {
-    // If the sender PC is a deoptimization point, get the original
-    // PC.  For MethodHandle call site the unextended_sp is stored in
-    // saved_fp.
-    if (sender_nm->is_deopt_mh_entry(_pc)) {
-      DEBUG_ONLY(verify_deopt_mh_original_pc(sender_nm, _fp));
-      _unextended_sp = _fp;
-    }
-    else if (sender_nm->is_deopt_entry(_pc)) {
+    // If the sender PC is a deoptimization point, get the original PC.
+    if (sender_nm->is_deopt_entry(_pc) ||
+        sender_nm->is_deopt_mh_entry(_pc)) {
       DEBUG_ONLY(verify_deopt_original_pc(sender_nm, _unextended_sp));
     }
-    else if (sender_nm->is_method_handle_return(_pc)) {
-      _unextended_sp = _fp;
-    }
   }
 }
 
--- a/hotspot/src/cpu/aarch64/vm/frame_aarch64.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/aarch64/vm/frame_aarch64.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -167,10 +167,7 @@
 
 #ifdef ASSERT
   // Used in frame::sender_for_{interpreter,compiled}_frame
-  static void verify_deopt_original_pc(   nmethod* nm, intptr_t* unextended_sp, bool is_method_handle_return = false);
-  static void verify_deopt_mh_original_pc(nmethod* nm, intptr_t* unextended_sp) {
-    verify_deopt_original_pc(nm, unextended_sp, true);
-  }
+  static void verify_deopt_original_pc(   nmethod* nm, intptr_t* unextended_sp);
 #endif
 
  public:
--- a/hotspot/src/cpu/aarch64/vm/frame_aarch64.inline.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/aarch64/vm/frame_aarch64.inline.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -47,12 +47,6 @@
 inline void frame::init(intptr_t* sp, intptr_t* fp, address pc) {
   intptr_t a = intptr_t(sp);
   intptr_t b = intptr_t(fp);
-#ifndef PRODUCT
-  if (fp)
-    if (sp > fp || (fp - sp > 0x100000))
-      for(;;)
-        asm("nop");
-#endif
   _sp = sp;
   _unextended_sp = sp;
   _fp = fp;
--- a/hotspot/src/cpu/aarch64/vm/macroAssembler_aarch64.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/aarch64/vm/macroAssembler_aarch64.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -3788,14 +3788,14 @@
 }
 
 void MacroAssembler::build_frame(int framesize) {
-  if (framesize == 0) {
-    // Is this even possible?
-    stp(rfp, lr, Address(pre(sp, -2 * wordSize)));
-  } else if (framesize < ((1 << 9) + 2 * wordSize)) {
+  assert(framesize > 0, "framesize must be > 0");
+  if (framesize < ((1 << 9) + 2 * wordSize)) {
     sub(sp, sp, framesize);
     stp(rfp, lr, Address(sp, framesize - 2 * wordSize));
+    if (PreserveFramePointer) add(rfp, sp, framesize - 2 * wordSize);
   } else {
     stp(rfp, lr, Address(pre(sp, -2 * wordSize)));
+    if (PreserveFramePointer) mov(rfp, sp);
     if (framesize < ((1 << 12) + 2 * wordSize))
       sub(sp, sp, framesize - 2 * wordSize);
     else {
@@ -3806,9 +3806,8 @@
 }
 
 void MacroAssembler::remove_frame(int framesize) {
-  if (framesize == 0) {
-    ldp(rfp, lr, Address(post(sp, 2 * wordSize)));
-  } else if (framesize < ((1 << 9) + 2 * wordSize)) {
+  assert(framesize > 0, "framesize must be > 0");
+  if (framesize < ((1 << 9) + 2 * wordSize)) {
     ldp(rfp, lr, Address(sp, framesize - 2 * wordSize));
     add(sp, sp, framesize);
   } else {
--- a/hotspot/src/cpu/aarch64/vm/register_definitions_aarch64.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/aarch64/vm/register_definitions_aarch64.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -149,7 +149,3 @@
 REGISTER_DEFINITION(Register, rheapbase);
 
 REGISTER_DEFINITION(Register, r31_sp);
-
-// TODO : x86 uses rbp to save SP in method handle code
-// we may need to do the same with fp
-// REGISTER_DEFINITION(Register, rbp_mh_SP_save)
--- a/hotspot/src/cpu/aarch64/vm/sharedRuntime_aarch64.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/aarch64/vm/sharedRuntime_aarch64.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -2995,21 +2995,6 @@
 
   // r0: exception handler
 
-  // Restore SP from BP if the exception PC is a MethodHandle call site.
-  __ ldrw(rscratch1, Address(rthread, JavaThread::is_method_handle_return_offset()));
-  // n.b. Intel uses special register rbp_mh_SP_save here but we will
-  // just hard wire rfp
-  __ cmpw(rscratch1, zr);
-  // the obvious way to conditionally copy rfp to sp if NE
-  // Label skip;
-  // __ br(Assembler::EQ, skip);
-  // __ mov(sp, rfp);
-  // __ bind(skip);
-  // same but branchless
-  __ mov(rscratch1, sp);
-  __ csel(rscratch1, rfp, rscratch1, Assembler::NE);
-  __ mov(sp, rscratch1);
-
   // We have a handler in r0 (could be deopt blob).
   __ mov(r8, r0);
 
--- a/hotspot/src/cpu/aarch64/vm/stubGenerator_aarch64.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/aarch64/vm/stubGenerator_aarch64.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1891,7 +1891,7 @@
     address start = __ pc();
       __ enter();
 
-      __ mov(rscratch1, len_reg);
+      __ mov(rscratch2, len_reg);
       __ ldrw(keylen, Address(key, arrayOopDesc::length_offset_in_bytes() - arrayOopDesc::base_offset_in_bytes(T_INT)));
 
       __ ld1(v0, __ T16B, rvec);
--- a/hotspot/src/cpu/ppc/vm/vm_version_ppc.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/ppc/vm/vm_version_ppc.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -629,7 +629,7 @@
   // Print the detection code.
   if (PrintAssembly) {
     ttyLocker ttyl;
-    tty->print_cr("Decoding dscr configuration stub at " INTPTR_FORMAT " before execution:", code);
+    tty->print_cr("Decoding dscr configuration stub at " INTPTR_FORMAT " before execution:", p2i(code));
     Disassembler::decode((u_char*)code, (u_char*)code_end, tty);
   }
 
--- a/hotspot/src/cpu/x86/vm/assembler_x86.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/assembler_x86.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -54,6 +54,36 @@
 #define BIND(label) bind(label); BLOCK_COMMENT(#label ":")
 // Implementation of AddressLiteral
 
+// A 2-D table for managing compressed displacement(disp8) on EVEX enabled platforms.
+unsigned char tuple_table[Assembler::EVEX_ETUP + 1][Assembler::AVX_512bit + 1] = {
+  // -----------------Table 4.5 -------------------- //
+  16, 32, 64,  // EVEX_FV(0)
+  4,  4,  4,   // EVEX_FV(1) - with Evex.b
+  16, 32, 64,  // EVEX_FV(2) - with Evex.w
+  8,  8,  8,   // EVEX_FV(3) - with Evex.w and Evex.b
+  8,  16, 32,  // EVEX_HV(0)
+  4,  4,  4,   // EVEX_HV(1) - with Evex.b
+  // -----------------Table 4.6 -------------------- //
+  16, 32, 64,  // EVEX_FVM(0)
+  1,  1,  1,   // EVEX_T1S(0)
+  2,  2,  2,   // EVEX_T1S(1)
+  4,  4,  4,   // EVEX_T1S(2)
+  8,  8,  8,   // EVEX_T1S(3)
+  4,  4,  4,   // EVEX_T1F(0)
+  8,  8,  8,   // EVEX_T1F(1)
+  8,  8,  8,   // EVEX_T2(0)
+  0,  16, 16,  // EVEX_T2(1)
+  0,  16, 16,  // EVEX_T4(0)
+  0,  0,  32,  // EVEX_T4(1)
+  0,  0,  32,  // EVEX_T8(0)
+  8,  16, 32,  // EVEX_HVM(0)
+  4,  8,  16,  // EVEX_QVM(0)
+  2,  4,  8,   // EVEX_OVM(0)
+  16, 16, 16,  // EVEX_M128(0)
+  8,  32, 64,  // EVEX_DUP(0)
+  0,  0,  0    // EVEX_NTUP
+};
+
 AddressLiteral::AddressLiteral(address target, relocInfo::relocType rtype) {
   _is_lval = false;
   _target = target;
@@ -183,8 +213,9 @@
 // make this go away someday
 void Assembler::emit_data(jint data, relocInfo::relocType rtype, int format) {
   if (rtype == relocInfo::none)
-        emit_int32(data);
-  else  emit_data(data, Relocation::spec_simple(rtype), format);
+    emit_int32(data);
+  else
+    emit_data(data, Relocation::spec_simple(rtype), format);
 }
 
 void Assembler::emit_data(jint data, RelocationHolder const& rspec, int format) {
@@ -273,6 +304,177 @@
 }
 
 
+bool Assembler::query_compressed_disp_byte(int disp, bool is_evex_inst, int vector_len,
+                                           int cur_tuple_type, int in_size_in_bits, int cur_encoding) {
+  int mod_idx = 0;
+  // We will test if the displacement fits the compressed format and if so
+  // apply the compression to the displacment iff the result is8bit.
+  if (VM_Version::supports_evex() && is_evex_inst) {
+    switch (cur_tuple_type) {
+    case EVEX_FV:
+      if ((cur_encoding & VEX_W) == VEX_W) {
+        mod_idx += 2 + ((cur_encoding & EVEX_Rb) == EVEX_Rb) ? 1 : 0;
+      } else {
+        mod_idx = ((cur_encoding & EVEX_Rb) == EVEX_Rb) ? 1 : 0;
+      }
+      break;
+
+    case EVEX_HV:
+      mod_idx = ((cur_encoding & EVEX_Rb) == EVEX_Rb) ? 1 : 0;
+      break;
+
+    case EVEX_FVM:
+      break;
+
+    case EVEX_T1S:
+      switch (in_size_in_bits) {
+      case EVEX_8bit:
+        break;
+
+      case EVEX_16bit:
+        mod_idx = 1;
+        break;
+
+      case EVEX_32bit:
+        mod_idx = 2;
+        break;
+
+      case EVEX_64bit:
+        mod_idx = 3;
+        break;
+      }
+      break;
+
+    case EVEX_T1F:
+    case EVEX_T2:
+    case EVEX_T4:
+      mod_idx = (in_size_in_bits == EVEX_64bit) ? 1 : 0;
+      break;
+
+    case EVEX_T8:
+      break;
+
+    case EVEX_HVM:
+      break;
+
+    case EVEX_QVM:
+      break;
+
+    case EVEX_OVM:
+      break;
+
+    case EVEX_M128:
+      break;
+
+    case EVEX_DUP:
+      break;
+
+    default:
+      assert(0, "no valid evex tuple_table entry");
+      break;
+    }
+
+    if (vector_len >= AVX_128bit && vector_len <= AVX_512bit) {
+      int disp_factor = tuple_table[cur_tuple_type + mod_idx][vector_len];
+      if ((disp % disp_factor) == 0) {
+        int new_disp = disp / disp_factor;
+        if ((-0x80 <= new_disp && new_disp < 0x80)) {
+          disp = new_disp;
+        }
+      } else {
+        return false;
+      }
+    }
+  }
+  return (-0x80 <= disp && disp < 0x80);
+}
+
+
+bool Assembler::emit_compressed_disp_byte(int &disp) {
+  int mod_idx = 0;
+  // We will test if the displacement fits the compressed format and if so
+  // apply the compression to the displacment iff the result is8bit.
+  if (VM_Version::supports_evex() && is_evex_instruction) {
+    switch (tuple_type) {
+    case EVEX_FV:
+      if ((evex_encoding & VEX_W) == VEX_W) {
+        mod_idx += 2 + ((evex_encoding & EVEX_Rb) == EVEX_Rb) ? 1 : 0;
+      } else {
+        mod_idx = ((evex_encoding & EVEX_Rb) == EVEX_Rb) ? 1 : 0;
+      }
+      break;
+
+    case EVEX_HV:
+      mod_idx = ((evex_encoding & EVEX_Rb) == EVEX_Rb) ? 1 : 0;
+      break;
+
+    case EVEX_FVM:
+      break;
+
+    case EVEX_T1S:
+      switch (input_size_in_bits) {
+      case EVEX_8bit:
+        break;
+
+      case EVEX_16bit:
+        mod_idx = 1;
+        break;
+
+      case EVEX_32bit:
+        mod_idx = 2;
+        break;
+
+      case EVEX_64bit:
+        mod_idx = 3;
+        break;
+      }
+      break;
+
+    case EVEX_T1F:
+    case EVEX_T2:
+    case EVEX_T4:
+      mod_idx = (input_size_in_bits == EVEX_64bit) ? 1 : 0;
+      break;
+
+    case EVEX_T8:
+      break;
+
+    case EVEX_HVM:
+      break;
+
+    case EVEX_QVM:
+      break;
+
+    case EVEX_OVM:
+      break;
+
+    case EVEX_M128:
+      break;
+
+    case EVEX_DUP:
+      break;
+
+    default:
+      assert(0, "no valid evex tuple_table entry");
+      break;
+    }
+
+    if (avx_vector_len >= AVX_128bit && avx_vector_len <= AVX_512bit) {
+      int disp_factor = tuple_table[tuple_type + mod_idx][avx_vector_len];
+      if ((disp % disp_factor) == 0) {
+        int new_disp = disp / disp_factor;
+        if (is8bit(new_disp)) {
+          disp = new_disp;
+        }
+      } else {
+        return false;
+      }
+    }
+  }
+  return is8bit(disp);
+}
+
+
 void Assembler::emit_operand(Register reg, Register base, Register index,
                              Address::ScaleFactor scale, int disp,
                              RelocationHolder const& rspec,
@@ -296,7 +498,7 @@
         assert(index != rsp, "illegal addressing mode");
         emit_int8(0x04 | regenc);
         emit_int8(scale << 6 | indexenc | baseenc);
-      } else if (is8bit(disp) && rtype == relocInfo::none) {
+      } else if (emit_compressed_disp_byte(disp) && rtype == relocInfo::none) {
         // [base + index*scale + imm8]
         // [01 reg 100][ss index base] imm8
         assert(index != rsp, "illegal addressing mode");
@@ -318,7 +520,7 @@
         // [00 reg 100][00 100 100]
         emit_int8(0x04 | regenc);
         emit_int8(0x24);
-      } else if (is8bit(disp) && rtype == relocInfo::none) {
+      } else if (emit_compressed_disp_byte(disp) && rtype == relocInfo::none) {
         // [rsp + imm8]
         // [01 reg 100][00 100 100] disp8
         emit_int8(0x44 | regenc);
@@ -339,7 +541,7 @@
         // [base]
         // [00 reg base]
         emit_int8(0x00 | regenc | baseenc);
-      } else if (is8bit(disp) && rtype == relocInfo::none) {
+      } else if (emit_compressed_disp_byte(disp) && rtype == relocInfo::none) {
         // [base + disp8]
         // [01 reg base] disp8
         emit_int8(0x40 | regenc | baseenc);
@@ -389,11 +591,20 @@
       emit_data(disp, rspec, disp32_operand);
     }
   }
+  is_evex_instruction = false;
 }
 
 void Assembler::emit_operand(XMMRegister reg, Register base, Register index,
                              Address::ScaleFactor scale, int disp,
                              RelocationHolder const& rspec) {
+  if (UseAVX > 2) {
+    int xreg_enc = reg->encoding();
+    if (xreg_enc > 15) {
+      XMMRegister new_reg = as_XMMRegister(xreg_enc & 0xf);
+      emit_operand((Register)new_reg, base, index, scale, disp, rspec);
+      return;
+    }
+  }
   emit_operand((Register)reg, base, index, scale, disp, rspec);
 }
 
@@ -686,6 +897,29 @@
     debug_only(has_disp32 = true); // has both kinds of operands!
     break;
 
+  case 0x62: // EVEX_4bytes
+    assert((UseAVX > 0), "shouldn't have EVEX prefix");
+    assert(ip == inst+1, "no prefixes allowed");
+    // no EVEX collisions, all instructions that have 0x62 opcodes
+    // have EVEX versions and are subopcodes of 0x66
+    ip++; // skip P0 and exmaine W in P1
+    is_64bit = ((VEX_W & *ip) == VEX_W);
+    ip++; // move to P2
+    ip++; // skip P2, move to opcode
+    // To find the end of instruction (which == end_pc_operand).
+    switch (0xFF & *ip) {
+    case 0x61: // pcmpestri r, r/a, #8
+    case 0x70: // pshufd r, r/a, #8
+    case 0x73: // psrldq r, #8
+      tail_size = 1;  // the imm8
+      break;
+    default:
+      break;
+    }
+    ip++; // skip opcode
+    debug_only(has_disp32 = true); // has both kinds of operands!
+    break;
+
   case 0xD1: // sal a, 1; sar a, 1; shl a, 1; shr a, 1
   case 0xD3: // sal a, %cl; sar a, %cl; shl a, %cl; shr a, %cl
   case 0xD9: // fld_s a; fst_s a; fstp_s a; fldcw a
@@ -985,12 +1219,22 @@
 
 void Assembler::addsd(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x58, dst, src, VEX_SIMD_F2);
+  if (VM_Version::supports_evex()) {
+    emit_simd_arith_q(0x58, dst, src, VEX_SIMD_F2);
+  } else {
+    emit_simd_arith(0x58, dst, src, VEX_SIMD_F2);
+  }
 }
 
 void Assembler::addsd(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x58, dst, src, VEX_SIMD_F2);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_64bit;
+    emit_simd_arith_q(0x58, dst, src, VEX_SIMD_F2);
+  } else {
+    emit_simd_arith(0x58, dst, src, VEX_SIMD_F2);
+  }
 }
 
 void Assembler::addss(XMMRegister dst, XMMRegister src) {
@@ -1000,20 +1244,26 @@
 
 void Assembler::addss(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+  }
   emit_simd_arith(0x58, dst, src, VEX_SIMD_F3);
 }
 
 void Assembler::aesdec(XMMRegister dst, Address src) {
   assert(VM_Version::supports_aes(), "");
   InstructionMark im(this);
-  simd_prefix(dst, dst, src, VEX_SIMD_66, VEX_OPCODE_0F_38);
+  simd_prefix(dst, dst, src, VEX_SIMD_66, false,
+              VEX_OPCODE_0F_38, false, AVX_128bit, true);
   emit_int8((unsigned char)0xDE);
   emit_operand(dst, src);
 }
 
 void Assembler::aesdec(XMMRegister dst, XMMRegister src) {
   assert(VM_Version::supports_aes(), "");
-  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_66, VEX_OPCODE_0F_38);
+  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_66, false,
+                                      VEX_OPCODE_0F_38, false, AVX_128bit, true);
   emit_int8((unsigned char)0xDE);
   emit_int8(0xC0 | encode);
 }
@@ -1021,14 +1271,16 @@
 void Assembler::aesdeclast(XMMRegister dst, Address src) {
   assert(VM_Version::supports_aes(), "");
   InstructionMark im(this);
-  simd_prefix(dst, dst, src, VEX_SIMD_66, VEX_OPCODE_0F_38);
+  simd_prefix(dst, dst, src, VEX_SIMD_66, false,
+              VEX_OPCODE_0F_38, false, AVX_128bit, true);
   emit_int8((unsigned char)0xDF);
   emit_operand(dst, src);
 }
 
 void Assembler::aesdeclast(XMMRegister dst, XMMRegister src) {
   assert(VM_Version::supports_aes(), "");
-  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_66, VEX_OPCODE_0F_38);
+  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_66, false,
+                                      VEX_OPCODE_0F_38, false, AVX_128bit, true);
   emit_int8((unsigned char)0xDF);
   emit_int8((unsigned char)(0xC0 | encode));
 }
@@ -1036,14 +1288,16 @@
 void Assembler::aesenc(XMMRegister dst, Address src) {
   assert(VM_Version::supports_aes(), "");
   InstructionMark im(this);
-  simd_prefix(dst, dst, src, VEX_SIMD_66, VEX_OPCODE_0F_38);
+  simd_prefix(dst, dst, src, VEX_SIMD_66, false,
+              VEX_OPCODE_0F_38, false, AVX_128bit, true);
   emit_int8((unsigned char)0xDC);
   emit_operand(dst, src);
 }
 
 void Assembler::aesenc(XMMRegister dst, XMMRegister src) {
   assert(VM_Version::supports_aes(), "");
-  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_66, VEX_OPCODE_0F_38);
+  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_66, false,
+                                      VEX_OPCODE_0F_38, false, AVX_128bit, true);
   emit_int8((unsigned char)0xDC);
   emit_int8(0xC0 | encode);
 }
@@ -1051,14 +1305,16 @@
 void Assembler::aesenclast(XMMRegister dst, Address src) {
   assert(VM_Version::supports_aes(), "");
   InstructionMark im(this);
-  simd_prefix(dst, dst, src, VEX_SIMD_66, VEX_OPCODE_0F_38);
+  simd_prefix(dst, dst, src, VEX_SIMD_66, false,
+              VEX_OPCODE_0F_38, false, AVX_128bit, true);
   emit_int8((unsigned char)0xDD);
   emit_operand(dst, src);
 }
 
 void Assembler::aesenclast(XMMRegister dst, XMMRegister src) {
   assert(VM_Version::supports_aes(), "");
-  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_66, VEX_OPCODE_0F_38);
+  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_66, false,
+                                      VEX_OPCODE_0F_38, false, AVX_128bit, true);
   emit_int8((unsigned char)0xDD);
   emit_int8((unsigned char)(0xC0 | encode));
 }
@@ -1091,7 +1347,7 @@
 
 void Assembler::andnl(Register dst, Register src1, Register src2) {
   assert(VM_Version::supports_bmi1(), "bit manipulation instructions not supported");
-  int encode = vex_prefix_0F38_and_encode(dst, src1, src2);
+  int encode = vex_prefix_0F38_and_encode(dst, src1, src2, false);
   emit_int8((unsigned char)0xF2);
   emit_int8((unsigned char)(0xC0 | encode));
 }
@@ -1099,7 +1355,7 @@
 void Assembler::andnl(Register dst, Register src1, Address src2) {
   InstructionMark im(this);
   assert(VM_Version::supports_bmi1(), "bit manipulation instructions not supported");
-  vex_prefix_0F38(dst, src1, src2);
+  vex_prefix_0F38(dst, src1, src2, false);
   emit_int8((unsigned char)0xF2);
   emit_operand(dst, src2);
 }
@@ -1126,7 +1382,7 @@
 
 void Assembler::blsil(Register dst, Register src) {
   assert(VM_Version::supports_bmi1(), "bit manipulation instructions not supported");
-  int encode = vex_prefix_0F38_and_encode(rbx, dst, src);
+  int encode = vex_prefix_0F38_and_encode(rbx, dst, src, false);
   emit_int8((unsigned char)0xF3);
   emit_int8((unsigned char)(0xC0 | encode));
 }
@@ -1134,14 +1390,14 @@
 void Assembler::blsil(Register dst, Address src) {
   InstructionMark im(this);
   assert(VM_Version::supports_bmi1(), "bit manipulation instructions not supported");
-  vex_prefix_0F38(rbx, dst, src);
+  vex_prefix_0F38(rbx, dst, src, false);
   emit_int8((unsigned char)0xF3);
   emit_operand(rbx, src);
 }
 
 void Assembler::blsmskl(Register dst, Register src) {
   assert(VM_Version::supports_bmi1(), "bit manipulation instructions not supported");
-  int encode = vex_prefix_0F38_and_encode(rdx, dst, src);
+  int encode = vex_prefix_0F38_and_encode(rdx, dst, src, false);
   emit_int8((unsigned char)0xF3);
   emit_int8((unsigned char)(0xC0 | encode));
 }
@@ -1149,14 +1405,14 @@
 void Assembler::blsmskl(Register dst, Address src) {
   InstructionMark im(this);
   assert(VM_Version::supports_bmi1(), "bit manipulation instructions not supported");
-  vex_prefix_0F38(rdx, dst, src);
+  vex_prefix_0F38(rdx, dst, src, false);
   emit_int8((unsigned char)0xF3);
   emit_operand(rdx, src);
 }
 
 void Assembler::blsrl(Register dst, Register src) {
   assert(VM_Version::supports_bmi1(), "bit manipulation instructions not supported");
-  int encode = vex_prefix_0F38_and_encode(rcx, dst, src);
+  int encode = vex_prefix_0F38_and_encode(rcx, dst, src, false);
   emit_int8((unsigned char)0xF3);
   emit_int8((unsigned char)(0xC0 | encode));
 }
@@ -1164,7 +1420,7 @@
 void Assembler::blsrl(Register dst, Address src) {
   InstructionMark im(this);
   assert(VM_Version::supports_bmi1(), "bit manipulation instructions not supported");
-  vex_prefix_0F38(rcx, dst, src);
+  vex_prefix_0F38(rcx, dst, src, false);
   emit_int8((unsigned char)0xF3);
   emit_operand(rcx, src);
 }
@@ -1312,22 +1568,36 @@
   // NOTE: dbx seems to decode this as comiss even though the
   // 0x66 is there. Strangly ucomisd comes out correct
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith_nonds(0x2F, dst, src, VEX_SIMD_66);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_64bit;
+    emit_simd_arith_nonds_q(0x2F, dst, src, VEX_SIMD_66, true);
+  } else {
+    emit_simd_arith_nonds(0x2F, dst, src, VEX_SIMD_66);
+  }
 }
 
 void Assembler::comisd(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith_nonds(0x2F, dst, src, VEX_SIMD_66);
+  if (VM_Version::supports_evex()) {
+    emit_simd_arith_nonds_q(0x2F, dst, src, VEX_SIMD_66, true);
+  } else {
+    emit_simd_arith_nonds(0x2F, dst, src, VEX_SIMD_66);
+  }
 }
 
 void Assembler::comiss(XMMRegister dst, Address src) {
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+  }
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
-  emit_simd_arith_nonds(0x2F, dst, src, VEX_SIMD_NONE);
+  emit_simd_arith_nonds(0x2F, dst, src, VEX_SIMD_NONE, true);
 }
 
 void Assembler::comiss(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
-  emit_simd_arith_nonds(0x2F, dst, src, VEX_SIMD_NONE);
+  emit_simd_arith_nonds(0x2F, dst, src, VEX_SIMD_NONE, true);
 }
 
 void Assembler::cpuid() {
@@ -1347,36 +1617,61 @@
 
 void Assembler::cvtsd2ss(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x5A, dst, src, VEX_SIMD_F2);
+  if (VM_Version::supports_evex()) {
+    emit_simd_arith_q(0x5A, dst, src, VEX_SIMD_F2);
+  } else {
+    emit_simd_arith(0x5A, dst, src, VEX_SIMD_F2);
+  }
 }
 
 void Assembler::cvtsd2ss(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x5A, dst, src, VEX_SIMD_F2);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1F;
+    input_size_in_bits = EVEX_64bit;
+    emit_simd_arith_q(0x5A, dst, src, VEX_SIMD_F2);
+  } else {
+    emit_simd_arith(0x5A, dst, src, VEX_SIMD_F2);
+  }
 }
 
 void Assembler::cvtsi2sdl(XMMRegister dst, Register src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_F2);
+  int encode = 0;
+  if (VM_Version::supports_evex()) {
+    encode = simd_prefix_and_encode_q(dst, dst, src, VEX_SIMD_F2, true);
+  } else {
+    encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_F2, false);
+  }
   emit_int8(0x2A);
   emit_int8((unsigned char)(0xC0 | encode));
 }
 
 void Assembler::cvtsi2sdl(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x2A, dst, src, VEX_SIMD_F2);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+    emit_simd_arith_q(0x2A, dst, src, VEX_SIMD_F2, true);
+  } else {
+    emit_simd_arith(0x2A, dst, src, VEX_SIMD_F2);
+  }
 }
 
 void Assembler::cvtsi2ssl(XMMRegister dst, Register src) {
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
-  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_F3);
+  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_F3, true);
   emit_int8(0x2A);
   emit_int8((unsigned char)(0xC0 | encode));
 }
 
 void Assembler::cvtsi2ssl(XMMRegister dst, Address src) {
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+  }
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
-  emit_simd_arith(0x2A, dst, src, VEX_SIMD_F3);
+  emit_simd_arith(0x2A, dst, src, VEX_SIMD_F3, true);
 }
 
 void Assembler::cvtss2sd(XMMRegister dst, XMMRegister src) {
@@ -1385,6 +1680,10 @@
 }
 
 void Assembler::cvtss2sd(XMMRegister dst, Address src) {
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+  }
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
   emit_simd_arith(0x5A, dst, src, VEX_SIMD_F3);
 }
@@ -1392,14 +1691,14 @@
 
 void Assembler::cvttsd2sil(Register dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  int encode = simd_prefix_and_encode(dst, src, VEX_SIMD_F2);
+  int encode = simd_prefix_and_encode(dst, src, VEX_SIMD_F2, VEX_OPCODE_0F, true);
   emit_int8(0x2C);
   emit_int8((unsigned char)(0xC0 | encode));
 }
 
 void Assembler::cvttss2sil(Register dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
-  int encode = simd_prefix_and_encode(dst, src, VEX_SIMD_F3);
+  int encode = simd_prefix_and_encode(dst, src, VEX_SIMD_F3, VEX_OPCODE_0F, true);
   emit_int8(0x2C);
   emit_int8((unsigned char)(0xC0 | encode));
 }
@@ -1414,15 +1713,29 @@
 
 void Assembler::divsd(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x5E, dst, src, VEX_SIMD_F2);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_64bit;
+    emit_simd_arith_q(0x5E, dst, src, VEX_SIMD_F2);
+  } else {
+    emit_simd_arith(0x5E, dst, src, VEX_SIMD_F2);
+  }
 }
 
 void Assembler::divsd(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x5E, dst, src, VEX_SIMD_F2);
+  if (VM_Version::supports_evex()) {
+    emit_simd_arith_q(0x5E, dst, src, VEX_SIMD_F2);
+  } else {
+    emit_simd_arith(0x5E, dst, src, VEX_SIMD_F2);
+  }
 }
 
 void Assembler::divss(XMMRegister dst, Address src) {
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+  }
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
   emit_simd_arith(0x5E, dst, src, VEX_SIMD_F3);
 }
@@ -1675,7 +1988,11 @@
 
 void Assembler::movapd(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith_nonds(0x28, dst, src, VEX_SIMD_66);
+  if (VM_Version::supports_evex()) {
+    emit_simd_arith_nonds_q(0x28, dst, src, VEX_SIMD_66, true);
+  } else {
+    emit_simd_arith_nonds(0x28, dst, src, VEX_SIMD_66);
+  }
 }
 
 void Assembler::movaps(XMMRegister dst, XMMRegister src) {
@@ -1685,7 +2002,8 @@
 
 void Assembler::movlhps(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
-  int encode = simd_prefix_and_encode(dst, src, src, VEX_SIMD_NONE);
+  int encode = simd_prefix_and_encode(dst, src, src, VEX_SIMD_NONE, true, VEX_OPCODE_0F,
+                                      false, AVX_128bit);
   emit_int8(0x16);
   emit_int8((unsigned char)(0xC0 | encode));
 }
@@ -1698,6 +2016,51 @@
   emit_operand(dst, src);
 }
 
+void Assembler::kmovq(KRegister dst, KRegister src) {
+  NOT_LP64(assert(VM_Version::supports_evex(), ""));
+  int encode = kreg_prefix_and_encode(dst, knoreg, src, VEX_SIMD_NONE,
+                                      true, VEX_OPCODE_0F, true);
+  emit_int8((unsigned char)0x90);
+  emit_int8((unsigned char)(0xC0 | encode));
+}
+
+void Assembler::kmovq(KRegister dst, Address src) {
+  NOT_LP64(assert(VM_Version::supports_evex(), ""));
+  int dst_enc = dst->encoding();
+  int nds_enc = 0;
+  vex_prefix(src, nds_enc, dst_enc, VEX_SIMD_NONE,
+             VEX_OPCODE_0F, true, AVX_128bit, true, true);
+  emit_int8((unsigned char)0x90);
+  emit_operand((Register)dst, src);
+}
+
+void Assembler::kmovq(Address dst, KRegister src) {
+  NOT_LP64(assert(VM_Version::supports_evex(), ""));
+  int src_enc = src->encoding();
+  int nds_enc = 0;
+  vex_prefix(dst, nds_enc, src_enc, VEX_SIMD_NONE,
+             VEX_OPCODE_0F, true, AVX_128bit, true, true);
+  emit_int8((unsigned char)0x90);
+  emit_operand((Register)src, dst);
+}
+
+void Assembler::kmovql(KRegister dst, Register src) {
+  NOT_LP64(assert(VM_Version::supports_evex(), ""));
+  bool supports_bw = VM_Version::supports_avx512bw();
+  VexSimdPrefix pre = supports_bw ? VEX_SIMD_F2 : VEX_SIMD_NONE;
+  int encode = kreg_prefix_and_encode(dst, knoreg, src, pre, true,
+                                      VEX_OPCODE_0F, supports_bw);
+  emit_int8((unsigned char)0x92);
+  emit_int8((unsigned char)(0xC0 | encode));
+}
+
+void Assembler::kmovdl(KRegister dst, Register src) {
+  NOT_LP64(assert(VM_Version::supports_evex(), ""));
+  VexSimdPrefix pre = VM_Version::supports_avx512bw() ? VEX_SIMD_F2 : VEX_SIMD_NONE;
+  int encode = kreg_prefix_and_encode(dst, knoreg, src, pre, true, VEX_OPCODE_0F, false);
+  emit_int8((unsigned char)0x92);
+  emit_int8((unsigned char)(0xC0 | encode));
+}
 
 void Assembler::movb(Address dst, int imm8) {
   InstructionMark im(this);
@@ -1718,7 +2081,7 @@
 
 void Assembler::movdl(XMMRegister dst, Register src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  int encode = simd_prefix_and_encode(dst, src, VEX_SIMD_66);
+  int encode = simd_prefix_and_encode(dst, src, VEX_SIMD_66, true);
   emit_int8(0x6E);
   emit_int8((unsigned char)(0xC0 | encode));
 }
@@ -1726,23 +2089,31 @@
 void Assembler::movdl(Register dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
   // swap src/dst to get correct prefix
-  int encode = simd_prefix_and_encode(src, dst, VEX_SIMD_66);
+  int encode = simd_prefix_and_encode(src, dst, VEX_SIMD_66, true);
   emit_int8(0x7E);
   emit_int8((unsigned char)(0xC0 | encode));
 }
 
 void Assembler::movdl(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  InstructionMark im(this);
-  simd_prefix(dst, src, VEX_SIMD_66);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+  }
+  InstructionMark im(this);
+  simd_prefix(dst, src, VEX_SIMD_66, true, VEX_OPCODE_0F);
   emit_int8(0x6E);
   emit_operand(dst, src);
 }
 
 void Assembler::movdl(Address dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  InstructionMark im(this);
-  simd_prefix(dst, src, VEX_SIMD_66);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+  }
+  InstructionMark im(this);
+  simd_prefix(dst, src, VEX_SIMD_66, true);
   emit_int8(0x7E);
   emit_operand(src, dst);
 }
@@ -1754,11 +2125,17 @@
 
 void Assembler::movdqa(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FVM;
+  }
   emit_simd_arith_nonds(0x6F, dst, src, VEX_SIMD_66);
 }
 
 void Assembler::movdqu(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FVM;
+  }
   emit_simd_arith_nonds(0x6F, dst, src, VEX_SIMD_F3);
 }
 
@@ -1769,8 +2146,11 @@
 
 void Assembler::movdqu(Address dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  InstructionMark im(this);
-  simd_prefix(dst, src, VEX_SIMD_F3);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FVM;
+  }
+  InstructionMark im(this);
+  simd_prefix(dst, src, VEX_SIMD_F3, false);
   emit_int8(0x7F);
   emit_operand(src, dst);
 }
@@ -1778,28 +2158,77 @@
 // Move Unaligned 256bit Vector
 void Assembler::vmovdqu(XMMRegister dst, XMMRegister src) {
   assert(UseAVX > 0, "");
-  bool vector256 = true;
-  int encode = vex_prefix_and_encode(dst, xnoreg, src, VEX_SIMD_F3, vector256);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FVM;
+  }
+  int vector_len = AVX_256bit;
+  int encode = vex_prefix_and_encode(dst, xnoreg, src, VEX_SIMD_F3, vector_len);
   emit_int8(0x6F);
   emit_int8((unsigned char)(0xC0 | encode));
 }
 
 void Assembler::vmovdqu(XMMRegister dst, Address src) {
   assert(UseAVX > 0, "");
-  InstructionMark im(this);
-  bool vector256 = true;
-  vex_prefix(dst, xnoreg, src, VEX_SIMD_F3, vector256);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FVM;
+  }
+  InstructionMark im(this);
+  int vector_len = AVX_256bit;
+  vex_prefix(dst, xnoreg, src, VEX_SIMD_F3, vector_len, false);
   emit_int8(0x6F);
   emit_operand(dst, src);
 }
 
 void Assembler::vmovdqu(Address dst, XMMRegister src) {
   assert(UseAVX > 0, "");
-  InstructionMark im(this);
-  bool vector256 = true;
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FVM;
+  }
+  InstructionMark im(this);
+  int vector_len = AVX_256bit;
   // swap src<->dst for encoding
   assert(src != xnoreg, "sanity");
-  vex_prefix(src, xnoreg, dst, VEX_SIMD_F3, vector256);
+  vex_prefix(src, xnoreg, dst, VEX_SIMD_F3, vector_len, false);
+  emit_int8(0x7F);
+  emit_operand(src, dst);
+}
+
+// Move Unaligned EVEX enabled Vector (programmable : 8,16,32,64)
+void Assembler::evmovdqu(XMMRegister dst, XMMRegister src, int vector_len) {
+  assert(UseAVX > 0, "");
+  int src_enc = src->encoding();
+  int dst_enc = dst->encoding();
+  int encode = vex_prefix_and_encode(dst_enc, 0, src_enc, VEX_SIMD_F3, VEX_OPCODE_0F,
+                                     true, vector_len, false, false);
+  emit_int8(0x6F);
+  emit_int8((unsigned char)(0xC0 | encode));
+}
+
+void Assembler::evmovdqu(XMMRegister dst, Address src, int vector_len) {
+  assert(UseAVX > 0, "");
+  InstructionMark im(this);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FVM;
+    vex_prefix_q(dst, xnoreg, src, VEX_SIMD_F3, vector_len, false);
+  } else {
+    vex_prefix(dst, xnoreg, src, VEX_SIMD_F3, vector_len, false);
+  }
+  emit_int8(0x6F);
+  emit_operand(dst, src);
+}
+
+void Assembler::evmovdqu(Address dst, XMMRegister src, int vector_len) {
+  assert(UseAVX > 0, "");
+  InstructionMark im(this);
+  assert(src != xnoreg, "sanity");
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FVM;
+    // swap src<->dst for encoding
+    vex_prefix_q(src, xnoreg, dst, VEX_SIMD_F3, vector_len, false);
+  } else {
+    // swap src<->dst for encoding
+    vex_prefix(src, xnoreg, dst, VEX_SIMD_F3, vector_len, false);
+  }
   emit_int8(0x7F);
   emit_operand(src, dst);
 }
@@ -1845,7 +2274,11 @@
 // The selection is done in MacroAssembler::movdbl() and movflt().
 void Assembler::movlpd(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x12, dst, src, VEX_SIMD_66);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_simd_arith(0x12, dst, src, VEX_SIMD_66, true);
 }
 
 void Assembler::movq( MMXRegister dst, Address src ) {
@@ -1871,7 +2304,13 @@
 void Assembler::movq(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
   InstructionMark im(this);
-  simd_prefix(dst, src, VEX_SIMD_F3);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_64bit;
+    simd_prefix_q(dst, xnoreg, src, VEX_SIMD_F3, true);
+  } else {
+    simd_prefix(dst, src, VEX_SIMD_F3, true, VEX_OPCODE_0F);
+  }
   emit_int8(0x7E);
   emit_operand(dst, src);
 }
@@ -1879,7 +2318,14 @@
 void Assembler::movq(Address dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
   InstructionMark im(this);
-  simd_prefix(dst, src, VEX_SIMD_66);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_64bit;
+    simd_prefix(src, xnoreg, dst, VEX_SIMD_66, true,
+                VEX_OPCODE_0F, true, AVX_128bit);
+  } else {
+    simd_prefix(dst, src, VEX_SIMD_66, true);
+  }
   emit_int8((unsigned char)0xD6);
   emit_operand(src, dst);
 }
@@ -1902,36 +2348,60 @@
 
 void Assembler::movsd(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x10, dst, src, VEX_SIMD_F2);
+  if (VM_Version::supports_evex()) {
+    emit_simd_arith_q(0x10, dst, src, VEX_SIMD_F2, true);
+  } else {
+    emit_simd_arith(0x10, dst, src, VEX_SIMD_F2);
+  }
 }
 
 void Assembler::movsd(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith_nonds(0x10, dst, src, VEX_SIMD_F2);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_64bit;
+    emit_simd_arith_nonds_q(0x10, dst, src, VEX_SIMD_F2, true);
+  } else {
+    emit_simd_arith_nonds(0x10, dst, src, VEX_SIMD_F2);
+  }
 }
 
 void Assembler::movsd(Address dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
   InstructionMark im(this);
-  simd_prefix(dst, src, VEX_SIMD_F2);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_64bit;
+    simd_prefix_q(src, xnoreg, dst, VEX_SIMD_F2);
+  } else {
+    simd_prefix(src, xnoreg, dst, VEX_SIMD_F2, false);
+  }
   emit_int8(0x11);
   emit_operand(src, dst);
 }
 
 void Assembler::movss(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
-  emit_simd_arith(0x10, dst, src, VEX_SIMD_F3);
+  emit_simd_arith(0x10, dst, src, VEX_SIMD_F3, true);
 }
 
 void Assembler::movss(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
-  emit_simd_arith_nonds(0x10, dst, src, VEX_SIMD_F3);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_simd_arith_nonds(0x10, dst, src, VEX_SIMD_F3, true);
 }
 
 void Assembler::movss(Address dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
-  InstructionMark im(this);
-  simd_prefix(dst, src, VEX_SIMD_F3);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+  }
+  InstructionMark im(this);
+  simd_prefix(dst, src, VEX_SIMD_F3, false);
   emit_int8(0x11);
   emit_operand(src, dst);
 }
@@ -2023,16 +2493,30 @@
 
 void Assembler::mulsd(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x59, dst, src, VEX_SIMD_F2);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_64bit;
+    emit_simd_arith_q(0x59, dst, src, VEX_SIMD_F2);
+  } else {
+    emit_simd_arith(0x59, dst, src, VEX_SIMD_F2);
+  }
 }
 
 void Assembler::mulsd(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x59, dst, src, VEX_SIMD_F2);
+  if (VM_Version::supports_evex()) {
+    emit_simd_arith_q(0x59, dst, src, VEX_SIMD_F2);
+  } else {
+    emit_simd_arith(0x59, dst, src, VEX_SIMD_F2);
+  }
 }
 
 void Assembler::mulss(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+  }
   emit_simd_arith(0x59, dst, src, VEX_SIMD_F3);
 }
 
@@ -2332,22 +2816,30 @@
 void Assembler::packuswb(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
   assert((UseAVX > 0), "SSE mode requires address alignment 16 bytes");
-  emit_simd_arith(0x67, dst, src, VEX_SIMD_66);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_simd_arith(0x67, dst, src, VEX_SIMD_66,
+                  false, (VM_Version::supports_avx512dq() == false));
 }
 
 void Assembler::packuswb(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x67, dst, src, VEX_SIMD_66);
-}
-
-void Assembler::vpackuswb(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0x67, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpermq(XMMRegister dst, XMMRegister src, int imm8, bool vector256) {
+  emit_simd_arith(0x67, dst, src, VEX_SIMD_66,
+                  false, (VM_Version::supports_avx512dq() == false));
+}
+
+void Assembler::vpackuswb(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(UseAVX > 0, "some form of AVX must be enabled");
+  emit_vex_arith(0x67, dst, nds, src, VEX_SIMD_66, vector_len,
+                 false, (VM_Version::supports_avx512dq() == false));
+}
+
+void Assembler::vpermq(XMMRegister dst, XMMRegister src, int imm8, int vector_len) {
   assert(VM_Version::supports_avx2(), "");
-  int encode = simd_prefix_and_encode(dst, xnoreg, src, VEX_SIMD_66, VEX_OPCODE_0F_3A, true, vector256);
+  int encode = simd_prefix_and_encode(dst, xnoreg, src, VEX_SIMD_66, false,
+                                      VEX_OPCODE_0F_3A, true, vector_len);
   emit_int8(0x00);
   emit_int8(0xC0 | encode);
   emit_int8(imm8);
@@ -2361,7 +2853,8 @@
 void Assembler::pcmpestri(XMMRegister dst, Address src, int imm8) {
   assert(VM_Version::supports_sse4_2(), "");
   InstructionMark im(this);
-  simd_prefix(dst, src, VEX_SIMD_66, VEX_OPCODE_0F_3A);
+  simd_prefix(dst, xnoreg, src, VEX_SIMD_66, false, VEX_OPCODE_0F_3A,
+              false, AVX_128bit, true);
   emit_int8(0x61);
   emit_operand(dst, src);
   emit_int8(imm8);
@@ -2369,7 +2862,8 @@
 
 void Assembler::pcmpestri(XMMRegister dst, XMMRegister src, int imm8) {
   assert(VM_Version::supports_sse4_2(), "");
-  int encode = simd_prefix_and_encode(dst, xnoreg, src, VEX_SIMD_66, VEX_OPCODE_0F_3A);
+  int encode = simd_prefix_and_encode(dst, xnoreg, src, VEX_SIMD_66, false,
+                                      VEX_OPCODE_0F_3A, false, AVX_128bit, true);
   emit_int8(0x61);
   emit_int8((unsigned char)(0xC0 | encode));
   emit_int8(imm8);
@@ -2377,7 +2871,8 @@
 
 void Assembler::pextrd(Register dst, XMMRegister src, int imm8) {
   assert(VM_Version::supports_sse4_1(), "");
-  int encode = simd_prefix_and_encode(as_XMMRegister(dst->encoding()), xnoreg, src, VEX_SIMD_66, VEX_OPCODE_0F_3A, false);
+  int encode = simd_prefix_and_encode(as_XMMRegister(dst->encoding()), xnoreg, src, VEX_SIMD_66, true, VEX_OPCODE_0F_3A,
+                                      false, AVX_128bit, (VM_Version::supports_avx512dq() == false));
   emit_int8(0x16);
   emit_int8((unsigned char)(0xC0 | encode));
   emit_int8(imm8);
@@ -2385,7 +2880,8 @@
 
 void Assembler::pextrq(Register dst, XMMRegister src, int imm8) {
   assert(VM_Version::supports_sse4_1(), "");
-  int encode = simd_prefix_and_encode(as_XMMRegister(dst->encoding()), xnoreg, src, VEX_SIMD_66, VEX_OPCODE_0F_3A, true);
+  int encode = simd_prefix_and_encode(as_XMMRegister(dst->encoding()), xnoreg, src, VEX_SIMD_66, true, VEX_OPCODE_0F_3A,
+                                      false, AVX_128bit, (VM_Version::supports_avx512dq() == false));
   emit_int8(0x16);
   emit_int8((unsigned char)(0xC0 | encode));
   emit_int8(imm8);
@@ -2393,7 +2889,8 @@
 
 void Assembler::pinsrd(XMMRegister dst, Register src, int imm8) {
   assert(VM_Version::supports_sse4_1(), "");
-  int encode = simd_prefix_and_encode(dst, dst, as_XMMRegister(src->encoding()), VEX_SIMD_66, VEX_OPCODE_0F_3A, false);
+  int encode = simd_prefix_and_encode(dst, dst, as_XMMRegister(src->encoding()), VEX_SIMD_66, true, VEX_OPCODE_0F_3A,
+                                      false, AVX_128bit, (VM_Version::supports_avx512dq() == false));
   emit_int8(0x22);
   emit_int8((unsigned char)(0xC0 | encode));
   emit_int8(imm8);
@@ -2401,7 +2898,8 @@
 
 void Assembler::pinsrq(XMMRegister dst, Register src, int imm8) {
   assert(VM_Version::supports_sse4_1(), "");
-  int encode = simd_prefix_and_encode(dst, dst, as_XMMRegister(src->encoding()), VEX_SIMD_66, VEX_OPCODE_0F_3A, true);
+  int encode = simd_prefix_and_encode(dst, dst, as_XMMRegister(src->encoding()), VEX_SIMD_66, true, VEX_OPCODE_0F_3A,
+                                      false, AVX_128bit, (VM_Version::supports_avx512dq() == false));
   emit_int8(0x22);
   emit_int8((unsigned char)(0xC0 | encode));
   emit_int8(imm8);
@@ -2409,15 +2907,18 @@
 
 void Assembler::pmovzxbw(XMMRegister dst, Address src) {
   assert(VM_Version::supports_sse4_1(), "");
-  InstructionMark im(this);
-  simd_prefix(dst, src, VEX_SIMD_66, VEX_OPCODE_0F_38);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_HVM;
+  }
+  InstructionMark im(this);
+  simd_prefix(dst, src, VEX_SIMD_66, false, VEX_OPCODE_0F_38);
   emit_int8(0x30);
   emit_operand(dst, src);
 }
 
 void Assembler::pmovzxbw(XMMRegister dst, XMMRegister src) {
   assert(VM_Version::supports_sse4_1(), "");
-  int encode = simd_prefix_and_encode(dst, xnoreg, src, VEX_SIMD_66, VEX_OPCODE_0F_38);
+  int encode = simd_prefix_and_encode(dst, xnoreg, src, VEX_SIMD_66, false, VEX_OPCODE_0F_38);
   emit_int8(0x30);
   emit_int8((unsigned char)(0xC0 | encode));
 }
@@ -2520,15 +3021,20 @@
 
 void Assembler::pshufb(XMMRegister dst, XMMRegister src) {
   assert(VM_Version::supports_ssse3(), "");
-  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_66, VEX_OPCODE_0F_38);
+  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_66, false, VEX_OPCODE_0F_38,
+                                      false, AVX_128bit, (VM_Version::supports_avx512bw() == false));
   emit_int8(0x00);
   emit_int8((unsigned char)(0xC0 | encode));
 }
 
 void Assembler::pshufb(XMMRegister dst, Address src) {
   assert(VM_Version::supports_ssse3(), "");
-  InstructionMark im(this);
-  simd_prefix(dst, dst, src, VEX_SIMD_66, VEX_OPCODE_0F_38);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FVM;
+  }
+  InstructionMark im(this);
+  simd_prefix(dst, dst, src, VEX_SIMD_66, false, VEX_OPCODE_0F_38,
+              false, AVX_128bit, (VM_Version::supports_avx512bw() == false));
   emit_int8(0x00);
   emit_operand(dst, src);
 }
@@ -2545,8 +3051,12 @@
   assert(isByte(mode), "invalid value");
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
   assert((UseAVX > 0), "SSE mode requires address alignment 16 bytes");
-  InstructionMark im(this);
-  simd_prefix(dst, src, VEX_SIMD_66);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_32bit;
+  }
+  InstructionMark im(this);
+  simd_prefix(dst, src, VEX_SIMD_66, false);
   emit_int8(0x70);
   emit_operand(dst, src);
   emit_int8(mode & 0xFF);
@@ -2555,7 +3065,8 @@
 void Assembler::pshuflw(XMMRegister dst, XMMRegister src, int mode) {
   assert(isByte(mode), "invalid value");
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith_nonds(0x70, dst, src, VEX_SIMD_F2);
+  emit_simd_arith_nonds(0x70, dst, src, VEX_SIMD_F2, false,
+                        (VM_Version::supports_avx512bw() == false));
   emit_int8(mode & 0xFF);
 }
 
@@ -2563,8 +3074,12 @@
   assert(isByte(mode), "invalid value");
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
   assert((UseAVX > 0), "SSE mode requires address alignment 16 bytes");
-  InstructionMark im(this);
-  simd_prefix(dst, src, VEX_SIMD_F2);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FVM;
+  }
+  InstructionMark im(this);
+  simd_prefix(dst, xnoreg, src, VEX_SIMD_F2, false, VEX_OPCODE_0F,
+              false, AVX_128bit, (VM_Version::supports_avx512bw() == false));
   emit_int8(0x70);
   emit_operand(dst, src);
   emit_int8(mode & 0xFF);
@@ -2573,7 +3088,8 @@
 void Assembler::psrldq(XMMRegister dst, int shift) {
   // Shift 128 bit value in xmm register by number of bytes.
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  int encode = simd_prefix_and_encode(xmm3, dst, dst, VEX_SIMD_66);
+  int encode = simd_prefix_and_encode(xmm3, dst, dst, VEX_SIMD_66, true, VEX_OPCODE_0F,
+                                      false, AVX_128bit, (VM_Version::supports_avx512bw() == false));
   emit_int8(0x73);
   emit_int8((unsigned char)(0xC0 | encode));
   emit_int8(shift);
@@ -2583,14 +3099,15 @@
   assert(VM_Version::supports_sse4_1(), "");
   assert((UseAVX > 0), "SSE mode requires address alignment 16 bytes");
   InstructionMark im(this);
-  simd_prefix(dst, src, VEX_SIMD_66, VEX_OPCODE_0F_38);
+  simd_prefix(dst, src, VEX_SIMD_66, false, VEX_OPCODE_0F_38);
   emit_int8(0x17);
   emit_operand(dst, src);
 }
 
 void Assembler::ptest(XMMRegister dst, XMMRegister src) {
   assert(VM_Version::supports_sse4_1(), "");
-  int encode = simd_prefix_and_encode(dst, xnoreg, src, VEX_SIMD_66, VEX_OPCODE_0F_38);
+  int encode = simd_prefix_and_encode(dst, xnoreg, src, VEX_SIMD_66,
+                                      false, VEX_OPCODE_0F_38);
   emit_int8(0x17);
   emit_int8((unsigned char)(0xC0 | encode));
 }
@@ -2598,19 +3115,20 @@
 void Assembler::vptest(XMMRegister dst, Address src) {
   assert(VM_Version::supports_avx(), "");
   InstructionMark im(this);
-  bool vector256 = true;
+  int vector_len = AVX_256bit;
   assert(dst != xnoreg, "sanity");
   int dst_enc = dst->encoding();
   // swap src<->dst for encoding
-  vex_prefix(src, 0, dst_enc, VEX_SIMD_66, VEX_OPCODE_0F_38, false, vector256);
+  vex_prefix(src, 0, dst_enc, VEX_SIMD_66, VEX_OPCODE_0F_38, false, vector_len);
   emit_int8(0x17);
   emit_operand(dst, src);
 }
 
 void Assembler::vptest(XMMRegister dst, XMMRegister src) {
   assert(VM_Version::supports_avx(), "");
-  bool vector256 = true;
-  int encode = vex_prefix_and_encode(dst, xnoreg, src, VEX_SIMD_66, vector256, VEX_OPCODE_0F_38);
+  int vector_len = AVX_256bit;
+  int encode = vex_prefix_and_encode(dst, xnoreg, src, VEX_SIMD_66,
+                                     vector_len, VEX_OPCODE_0F_38);
   emit_int8(0x17);
   emit_int8((unsigned char)(0xC0 | encode));
 }
@@ -2618,6 +3136,9 @@
 void Assembler::punpcklbw(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
   assert((UseAVX > 0), "SSE mode requires address alignment 16 bytes");
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FVM;
+  }
   emit_simd_arith(0x60, dst, src, VEX_SIMD_66);
 }
 
@@ -2629,6 +3150,10 @@
 void Assembler::punpckldq(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
   assert((UseAVX > 0), "SSE mode requires address alignment 16 bytes");
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_32bit;
+  }
   emit_simd_arith(0x62, dst, src, VEX_SIMD_66);
 }
 
@@ -2838,12 +3363,22 @@
 
 void Assembler::sqrtsd(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x51, dst, src, VEX_SIMD_F2);
+  if (VM_Version::supports_evex()) {
+    emit_simd_arith_q(0x51, dst, src, VEX_SIMD_F2);
+  } else {
+    emit_simd_arith(0x51, dst, src, VEX_SIMD_F2);
+  }
 }
 
 void Assembler::sqrtsd(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x51, dst, src, VEX_SIMD_F2);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_64bit;
+    emit_simd_arith_q(0x51, dst, src, VEX_SIMD_F2);
+  } else {
+    emit_simd_arith(0x51, dst, src, VEX_SIMD_F2);
+  }
 }
 
 void Assembler::sqrtss(XMMRegister dst, XMMRegister src) {
@@ -2857,6 +3392,10 @@
 
 void Assembler::sqrtss(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+  }
   emit_simd_arith(0x51, dst, src, VEX_SIMD_F3);
 }
 
@@ -2907,12 +3446,20 @@
 
 void Assembler::subsd(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x5C, dst, src, VEX_SIMD_F2);
+  if (VM_Version::supports_evex()) {
+    emit_simd_arith_q(0x5C, dst, src, VEX_SIMD_F2);
+  } else {
+    emit_simd_arith(0x5C, dst, src, VEX_SIMD_F2);
+  }
 }
 
 void Assembler::subsd(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x5C, dst, src, VEX_SIMD_F2);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_64bit;
+  }
+  emit_simd_arith_q(0x5C, dst, src, VEX_SIMD_F2);
 }
 
 void Assembler::subss(XMMRegister dst, XMMRegister src) {
@@ -2922,6 +3469,10 @@
 
 void Assembler::subss(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+  }
   emit_simd_arith(0x5C, dst, src, VEX_SIMD_F3);
 }
 
@@ -2978,22 +3529,36 @@
 
 void Assembler::ucomisd(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith_nonds(0x2E, dst, src, VEX_SIMD_66);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_64bit;
+    emit_simd_arith_nonds_q(0x2E, dst, src, VEX_SIMD_66, true);
+  } else {
+    emit_simd_arith_nonds(0x2E, dst, src, VEX_SIMD_66);
+  }
 }
 
 void Assembler::ucomisd(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith_nonds(0x2E, dst, src, VEX_SIMD_66);
+  if (VM_Version::supports_evex()) {
+    emit_simd_arith_nonds_q(0x2E, dst, src, VEX_SIMD_66, true);
+  } else {
+    emit_simd_arith_nonds(0x2E, dst, src, VEX_SIMD_66);
+  }
 }
 
 void Assembler::ucomiss(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
-  emit_simd_arith_nonds(0x2E, dst, src, VEX_SIMD_NONE);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_simd_arith_nonds(0x2E, dst, src, VEX_SIMD_NONE, true);
 }
 
 void Assembler::ucomiss(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
-  emit_simd_arith_nonds(0x2E, dst, src, VEX_SIMD_NONE);
+  emit_simd_arith_nonds(0x2E, dst, src, VEX_SIMD_NONE, true);
 }
 
 void Assembler::xabort(int8_t imm8) {
@@ -3075,82 +3640,138 @@
 
 void Assembler::vaddsd(XMMRegister dst, XMMRegister nds, Address src) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x58, dst, nds, src, VEX_SIMD_F2, /* vector256 */ false);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_64bit;
+    emit_vex_arith_q(0x58, dst, nds, src, VEX_SIMD_F2, AVX_128bit);
+  } else {
+    emit_vex_arith(0x58, dst, nds, src, VEX_SIMD_F2, AVX_128bit);
+  }
 }
 
 void Assembler::vaddsd(XMMRegister dst, XMMRegister nds, XMMRegister src) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x58, dst, nds, src, VEX_SIMD_F2, /* vector256 */ false);
+  if (VM_Version::supports_evex()) {
+    emit_vex_arith_q(0x58, dst, nds, src, VEX_SIMD_F2, AVX_128bit);
+  } else {
+    emit_vex_arith(0x58, dst, nds, src, VEX_SIMD_F2, AVX_128bit);
+  }
 }
 
 void Assembler::vaddss(XMMRegister dst, XMMRegister nds, Address src) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x58, dst, nds, src, VEX_SIMD_F3, /* vector256 */ false);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_vex_arith(0x58, dst, nds, src, VEX_SIMD_F3, AVX_128bit);
 }
 
 void Assembler::vaddss(XMMRegister dst, XMMRegister nds, XMMRegister src) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x58, dst, nds, src, VEX_SIMD_F3, /* vector256 */ false);
+  emit_vex_arith(0x58, dst, nds, src, VEX_SIMD_F3, AVX_128bit);
 }
 
 void Assembler::vdivsd(XMMRegister dst, XMMRegister nds, Address src) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x5E, dst, nds, src, VEX_SIMD_F2, /* vector256 */ false);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_64bit;
+    emit_vex_arith_q(0x5E, dst, nds, src, VEX_SIMD_F2, AVX_128bit);
+  } else {
+    emit_vex_arith(0x5E, dst, nds, src, VEX_SIMD_F2, AVX_128bit);
+  }
 }
 
 void Assembler::vdivsd(XMMRegister dst, XMMRegister nds, XMMRegister src) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x5E, dst, nds, src, VEX_SIMD_F2, /* vector256 */ false);
+  if (VM_Version::supports_evex()) {
+    emit_vex_arith_q(0x5E, dst, nds, src, VEX_SIMD_F2, AVX_128bit);
+  } else {
+    emit_vex_arith(0x5E, dst, nds, src, VEX_SIMD_F2, AVX_128bit);
+  }
 }
 
 void Assembler::vdivss(XMMRegister dst, XMMRegister nds, Address src) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x5E, dst, nds, src, VEX_SIMD_F3, /* vector256 */ false);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_vex_arith(0x5E, dst, nds, src, VEX_SIMD_F3, AVX_128bit);
 }
 
 void Assembler::vdivss(XMMRegister dst, XMMRegister nds, XMMRegister src) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x5E, dst, nds, src, VEX_SIMD_F3, /* vector256 */ false);
+  emit_vex_arith(0x5E, dst, nds, src, VEX_SIMD_F3, AVX_128bit);
 }
 
 void Assembler::vmulsd(XMMRegister dst, XMMRegister nds, Address src) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x59, dst, nds, src, VEX_SIMD_F2, /* vector256 */ false);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_64bit;
+    emit_vex_arith_q(0x59, dst, nds, src, VEX_SIMD_F2, AVX_128bit);
+  } else {
+    emit_vex_arith(0x59, dst, nds, src, VEX_SIMD_F2, AVX_128bit);
+  }
 }
 
 void Assembler::vmulsd(XMMRegister dst, XMMRegister nds, XMMRegister src) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x59, dst, nds, src, VEX_SIMD_F2, /* vector256 */ false);
+  if (VM_Version::supports_evex()) {
+    emit_vex_arith_q(0x59, dst, nds, src, VEX_SIMD_F2, AVX_128bit);
+  } else {
+    emit_vex_arith(0x59, dst, nds, src, VEX_SIMD_F2, AVX_128bit);
+  }
 }
 
 void Assembler::vmulss(XMMRegister dst, XMMRegister nds, Address src) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x59, dst, nds, src, VEX_SIMD_F3, /* vector256 */ false);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_vex_arith(0x59, dst, nds, src, VEX_SIMD_F3, AVX_128bit);
 }
 
 void Assembler::vmulss(XMMRegister dst, XMMRegister nds, XMMRegister src) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x59, dst, nds, src, VEX_SIMD_F3, /* vector256 */ false);
+  emit_vex_arith(0x59, dst, nds, src, VEX_SIMD_F3, AVX_128bit);
 }
 
 void Assembler::vsubsd(XMMRegister dst, XMMRegister nds, Address src) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x5C, dst, nds, src, VEX_SIMD_F2, /* vector256 */ false);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_64bit;
+    emit_vex_arith_q(0x5C, dst, nds, src, VEX_SIMD_F2, AVX_128bit);
+  } else {
+    emit_vex_arith(0x5C, dst, nds, src, VEX_SIMD_F2, AVX_128bit);
+  }
 }
 
 void Assembler::vsubsd(XMMRegister dst, XMMRegister nds, XMMRegister src) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x5C, dst, nds, src, VEX_SIMD_F2, /* vector256 */ false);
+  if (VM_Version::supports_evex()) {
+    emit_vex_arith_q(0x5C, dst, nds, src, VEX_SIMD_F2, AVX_128bit);
+  } else {
+    emit_vex_arith(0x5C, dst, nds, src, VEX_SIMD_F2, AVX_128bit);
+  }
 }
 
 void Assembler::vsubss(XMMRegister dst, XMMRegister nds, Address src) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x5C, dst, nds, src, VEX_SIMD_F3, /* vector256 */ false);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_vex_arith(0x5C, dst, nds, src, VEX_SIMD_F3, AVX_128bit);
 }
 
 void Assembler::vsubss(XMMRegister dst, XMMRegister nds, XMMRegister src) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x5C, dst, nds, src, VEX_SIMD_F3, /* vector256 */ false);
+  emit_vex_arith(0x5C, dst, nds, src, VEX_SIMD_F3, AVX_128bit);
 }
 
 //====================VECTOR ARITHMETIC=====================================
@@ -3159,7 +3780,11 @@
 
 void Assembler::addpd(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x58, dst, src, VEX_SIMD_66);
+  if (VM_Version::supports_evex()) {
+    emit_simd_arith_q(0x58, dst, src, VEX_SIMD_66);
+  } else {
+    emit_simd_arith(0x58, dst, src, VEX_SIMD_66);
+  }
 }
 
 void Assembler::addps(XMMRegister dst, XMMRegister src) {
@@ -3167,29 +3792,47 @@
   emit_simd_arith(0x58, dst, src, VEX_SIMD_NONE);
 }
 
-void Assembler::vaddpd(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
+void Assembler::vaddpd(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x58, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vaddps(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
+  if (VM_Version::supports_evex()) {
+    emit_vex_arith_q(0x58, dst, nds, src, VEX_SIMD_66, vector_len);
+  } else {
+    emit_vex_arith(0x58, dst, nds, src, VEX_SIMD_66, vector_len);
+  }
+}
+
+void Assembler::vaddps(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(VM_Version::supports_avx(), "");
+  emit_vex_arith(0x58, dst, nds, src, VEX_SIMD_NONE, vector_len);
+}
+
+void Assembler::vaddpd(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x58, dst, nds, src, VEX_SIMD_NONE, vector256);
-}
-
-void Assembler::vaddpd(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_64bit;
+    emit_vex_arith_q(0x58, dst, nds, src, VEX_SIMD_66, vector_len);
+  } else {
+    emit_vex_arith(0x58, dst, nds, src, VEX_SIMD_66, vector_len);
+  }
+}
+
+void Assembler::vaddps(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x58, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vaddps(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
-  assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x58, dst, nds, src, VEX_SIMD_NONE, vector256);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_vex_arith(0x58, dst, nds, src, VEX_SIMD_NONE, vector_len);
 }
 
 void Assembler::subpd(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x5C, dst, src, VEX_SIMD_66);
+  if (VM_Version::supports_evex()) {
+    emit_simd_arith_q(0x5C, dst, src, VEX_SIMD_66);
+  } else {
+    emit_simd_arith(0x5C, dst, src, VEX_SIMD_66);
+  }
 }
 
 void Assembler::subps(XMMRegister dst, XMMRegister src) {
@@ -3197,29 +3840,47 @@
   emit_simd_arith(0x5C, dst, src, VEX_SIMD_NONE);
 }
 
-void Assembler::vsubpd(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
+void Assembler::vsubpd(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x5C, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vsubps(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
+  if (VM_Version::supports_evex()) {
+    emit_vex_arith_q(0x5C, dst, nds, src, VEX_SIMD_66, vector_len);
+  } else {
+    emit_vex_arith(0x5C, dst, nds, src, VEX_SIMD_66, vector_len);
+  }
+}
+
+void Assembler::vsubps(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(VM_Version::supports_avx(), "");
+  emit_vex_arith(0x5C, dst, nds, src, VEX_SIMD_NONE, vector_len);
+}
+
+void Assembler::vsubpd(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x5C, dst, nds, src, VEX_SIMD_NONE, vector256);
-}
-
-void Assembler::vsubpd(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_64bit;
+    emit_vex_arith_q(0x5C, dst, nds, src, VEX_SIMD_66, vector_len);
+  } else {
+    emit_vex_arith(0x5C, dst, nds, src, VEX_SIMD_66, vector_len);
+  }
+}
+
+void Assembler::vsubps(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x5C, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vsubps(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
-  assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x5C, dst, nds, src, VEX_SIMD_NONE, vector256);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_vex_arith(0x5C, dst, nds, src, VEX_SIMD_NONE, vector_len);
 }
 
 void Assembler::mulpd(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x59, dst, src, VEX_SIMD_66);
+  if (VM_Version::supports_evex()) {
+    emit_simd_arith_q(0x59, dst, src, VEX_SIMD_66);
+  } else {
+    emit_simd_arith(0x59, dst, src, VEX_SIMD_66);
+  }
 }
 
 void Assembler::mulps(XMMRegister dst, XMMRegister src) {
@@ -3227,29 +3888,47 @@
   emit_simd_arith(0x59, dst, src, VEX_SIMD_NONE);
 }
 
-void Assembler::vmulpd(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
+void Assembler::vmulpd(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x59, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vmulps(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
+  if (VM_Version::supports_evex()) {
+    emit_vex_arith_q(0x59, dst, nds, src, VEX_SIMD_66, vector_len);
+  } else {
+    emit_vex_arith(0x59, dst, nds, src, VEX_SIMD_66, vector_len);
+  }
+}
+
+void Assembler::vmulps(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(VM_Version::supports_avx(), "");
+  emit_vex_arith(0x59, dst, nds, src, VEX_SIMD_NONE, vector_len);
+}
+
+void Assembler::vmulpd(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x59, dst, nds, src, VEX_SIMD_NONE, vector256);
-}
-
-void Assembler::vmulpd(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_64bit;
+    emit_vex_arith_q(0x59, dst, nds, src, VEX_SIMD_66, vector_len);
+  } else {
+    emit_vex_arith(0x59, dst, nds, src, VEX_SIMD_66, vector_len);
+  }
+}
+
+void Assembler::vmulps(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x59, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vmulps(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
-  assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x59, dst, nds, src, VEX_SIMD_NONE, vector256);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_vex_arith(0x59, dst, nds, src, VEX_SIMD_NONE, vector_len);
 }
 
 void Assembler::divpd(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x5E, dst, src, VEX_SIMD_66);
+  if (VM_Version::supports_evex()) {
+    emit_simd_arith_q(0x5E, dst, src, VEX_SIMD_66);
+  } else {
+    emit_simd_arith(0x5E, dst, src, VEX_SIMD_66);
+  }
 }
 
 void Assembler::divps(XMMRegister dst, XMMRegister src) {
@@ -3257,118 +3936,199 @@
   emit_simd_arith(0x5E, dst, src, VEX_SIMD_NONE);
 }
 
-void Assembler::vdivpd(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
+void Assembler::vdivpd(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x5E, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vdivps(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
+  if (VM_Version::supports_evex()) {
+    emit_vex_arith_q(0x5E, dst, nds, src, VEX_SIMD_66, vector_len);
+  } else {
+    emit_vex_arith(0x5E, dst, nds, src, VEX_SIMD_66, vector_len);
+  }
+}
+
+void Assembler::vdivps(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(VM_Version::supports_avx(), "");
+  emit_vex_arith(0x5E, dst, nds, src, VEX_SIMD_NONE, vector_len);
+}
+
+void Assembler::vdivpd(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x5E, dst, nds, src, VEX_SIMD_NONE, vector256);
-}
-
-void Assembler::vdivpd(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_64bit;
+    emit_vex_arith_q(0x5E, dst, nds, src, VEX_SIMD_66, vector_len);
+  } else {
+    emit_vex_arith(0x5E, dst, nds, src, VEX_SIMD_66, vector_len);
+  }
+}
+
+void Assembler::vdivps(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x5E, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vdivps(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
-  assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x5E, dst, nds, src, VEX_SIMD_NONE, vector256);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_vex_arith(0x5E, dst, nds, src, VEX_SIMD_NONE, vector_len);
 }
 
 void Assembler::andpd(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x54, dst, src, VEX_SIMD_66);
+  if (VM_Version::supports_evex() && VM_Version::supports_avx512dq()) {
+    emit_simd_arith_q(0x54, dst, src, VEX_SIMD_66);
+  } else {
+    emit_simd_arith(0x54, dst, src, VEX_SIMD_66, false, true);
+  }
 }
 
 void Assembler::andps(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
-  emit_simd_arith(0x54, dst, src, VEX_SIMD_NONE);
+  emit_simd_arith(0x54, dst, src, VEX_SIMD_NONE, false,
+                  (VM_Version::supports_avx512dq() == false));
 }
 
 void Assembler::andps(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
-  emit_simd_arith(0x54, dst, src, VEX_SIMD_NONE);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_simd_arith(0x54, dst, src, VEX_SIMD_NONE,
+                  false, (VM_Version::supports_avx512dq() == false));
 }
 
 void Assembler::andpd(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x54, dst, src, VEX_SIMD_66);
-}
-
-void Assembler::vandpd(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
+  if (VM_Version::supports_evex() && VM_Version::supports_avx512dq()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_64bit;
+    emit_simd_arith_q(0x54, dst, src, VEX_SIMD_66);
+  } else {
+    emit_simd_arith(0x54, dst, src, VEX_SIMD_66, false, true);
+  }
+}
+
+void Assembler::vandpd(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x54, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vandps(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
+  if (VM_Version::supports_evex() && VM_Version::supports_avx512dq()) {
+    emit_vex_arith_q(0x54, dst, nds, src, VEX_SIMD_66, vector_len);
+  } else {
+    emit_vex_arith(0x54, dst, nds, src, VEX_SIMD_66, vector_len, true);
+  }
+}
+
+void Assembler::vandps(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x54, dst, nds, src, VEX_SIMD_NONE, vector256);
-}
-
-void Assembler::vandpd(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
+  bool legacy_mode = (VM_Version::supports_avx512dq() == false);
+  emit_vex_arith(0x54, dst, nds, src, VEX_SIMD_NONE, vector_len, legacy_mode);
+}
+
+void Assembler::vandpd(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x54, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vandps(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
+  if (VM_Version::supports_evex() && VM_Version::supports_avx512dq()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_64bit;
+    emit_vex_arith_q(0x54, dst, nds, src, VEX_SIMD_66, vector_len);
+  } else {
+    emit_vex_arith(0x54, dst, nds, src, VEX_SIMD_66, vector_len, true);
+  }
+}
+
+void Assembler::vandps(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x54, dst, nds, src, VEX_SIMD_NONE, vector256);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_vex_arith(0x54, dst, nds, src, VEX_SIMD_NONE, vector_len,
+                 (VM_Version::supports_avx512dq() == false));
 }
 
 void Assembler::xorpd(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x57, dst, src, VEX_SIMD_66);
+  if (VM_Version::supports_evex() && VM_Version::supports_avx512dq()) {
+    emit_simd_arith_q(0x57, dst, src, VEX_SIMD_66);
+  } else {
+    emit_simd_arith(0x57, dst, src, VEX_SIMD_66, false, true);
+  }
 }
 
 void Assembler::xorps(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
-  emit_simd_arith(0x57, dst, src, VEX_SIMD_NONE);
+  emit_simd_arith(0x57, dst, src, VEX_SIMD_NONE,
+                  false, (VM_Version::supports_avx512dq() == false));
 }
 
 void Assembler::xorpd(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0x57, dst, src, VEX_SIMD_66);
+  if (VM_Version::supports_evex() && VM_Version::supports_avx512dq()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_64bit;
+    emit_simd_arith_q(0x57, dst, src, VEX_SIMD_66);
+  } else {
+    emit_simd_arith(0x57, dst, src, VEX_SIMD_66, false, true);
+  }
 }
 
 void Assembler::xorps(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
-  emit_simd_arith(0x57, dst, src, VEX_SIMD_NONE);
-}
-
-void Assembler::vxorpd(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_simd_arith(0x57, dst, src, VEX_SIMD_NONE, false,
+                  (VM_Version::supports_avx512dq() == false));
+}
+
+void Assembler::vxorpd(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x57, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vxorps(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
+  if (VM_Version::supports_evex() && VM_Version::supports_avx512dq()) {
+    emit_vex_arith_q(0x57, dst, nds, src, VEX_SIMD_66, vector_len);
+  } else {
+    emit_vex_arith(0x57, dst, nds, src, VEX_SIMD_66, vector_len, true);
+  }
+}
+
+void Assembler::vxorps(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x57, dst, nds, src, VEX_SIMD_NONE, vector256);
-}
-
-void Assembler::vxorpd(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
+  emit_vex_arith(0x57, dst, nds, src, VEX_SIMD_NONE, vector_len,
+                 (VM_Version::supports_avx512dq() == false));
+}
+
+void Assembler::vxorpd(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x57, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vxorps(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
+  if (VM_Version::supports_evex() && VM_Version::supports_avx512dq()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_64bit;
+    emit_vex_arith_q(0x57, dst, nds, src, VEX_SIMD_66, vector_len);
+  } else {
+    emit_vex_arith(0x57, dst, nds, src, VEX_SIMD_66, vector_len, true);
+  }
+}
+
+void Assembler::vxorps(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
   assert(VM_Version::supports_avx(), "");
-  emit_vex_arith(0x57, dst, nds, src, VEX_SIMD_NONE, vector256);
-}
-
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_vex_arith(0x57, dst, nds, src, VEX_SIMD_NONE, vector_len,
+                 (VM_Version::supports_avx512dq() == false));
+}
 
 // Integer vector arithmetic
-void Assembler::vphaddw(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  int encode = vex_prefix_and_encode(dst, nds, src, VEX_SIMD_66, vector256, VEX_OPCODE_0F_38);
+void Assembler::vphaddw(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(VM_Version::supports_avx() && (vector_len == 0) ||
+         VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
+  int encode = vex_prefix_and_encode(dst, nds, src, VEX_SIMD_66, vector_len,
+                                     VEX_OPCODE_0F_38, true, false);
   emit_int8(0x01);
   emit_int8((unsigned char)(0xC0 | encode));
 }
 
-void Assembler::vphaddd(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  int encode = vex_prefix_and_encode(dst, nds, src, VEX_SIMD_66, vector256, VEX_OPCODE_0F_38);
+void Assembler::vphaddd(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(VM_Version::supports_avx() && (vector_len == 0) ||
+         VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
+  int encode = vex_prefix_and_encode(dst, nds, src, VEX_SIMD_66, vector_len,
+                                     VEX_OPCODE_0F_38, true, false);
   emit_int8(0x02);
   emit_int8((unsigned char)(0xC0 | encode));
 }
@@ -3390,61 +4150,89 @@
 
 void Assembler::paddq(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0xD4, dst, src, VEX_SIMD_66);
+  if (VM_Version::supports_evex()) {
+    emit_simd_arith_q(0xD4, dst, src, VEX_SIMD_66);
+  } else {
+    emit_simd_arith(0xD4, dst, src, VEX_SIMD_66);
+  }
 }
 
 void Assembler::phaddw(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse3(), ""));
-  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_66, VEX_OPCODE_0F_38);
+  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_66, false,
+                                      VEX_OPCODE_0F_38, false, AVX_128bit, true);
   emit_int8(0x01);
   emit_int8((unsigned char)(0xC0 | encode));
 }
 
 void Assembler::phaddd(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse3(), ""));
-  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_66, VEX_OPCODE_0F_38);
+  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_66, false,
+                                      VEX_OPCODE_0F_38, false, AVX_128bit, true);
   emit_int8(0x02);
   emit_int8((unsigned char)(0xC0 | encode));
 }
 
-void Assembler::vpaddb(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xFC, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpaddw(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xFD, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpaddd(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xFE, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpaddq(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xD4, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpaddb(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xFC, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpaddw(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xFD, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpaddd(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xFE, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpaddq(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xD4, dst, nds, src, VEX_SIMD_66, vector256);
+void Assembler::vpaddb(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  emit_vex_arith(0xFC, dst, nds, src, VEX_SIMD_66, vector_len,
+                 (VM_Version::supports_avx512bw() == false));
+}
+
+void Assembler::vpaddw(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  emit_vex_arith(0xFD, dst, nds, src, VEX_SIMD_66, vector_len,
+                 (VM_Version::supports_avx512bw() == false));
+}
+
+void Assembler::vpaddd(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  emit_vex_arith(0xFE, dst, nds, src, VEX_SIMD_66, vector_len);
+}
+
+void Assembler::vpaddq(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  if (VM_Version::supports_evex()) {
+    emit_vex_arith_q(0xD4, dst, nds, src, VEX_SIMD_66, vector_len);
+  } else {
+    emit_vex_arith(0xD4, dst, nds, src, VEX_SIMD_66, vector_len);
+  }
+}
+
+void Assembler::vpaddb(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FVM;
+  }
+  emit_vex_arith(0xFC, dst, nds, src, VEX_SIMD_66, vector_len);
+}
+
+void Assembler::vpaddw(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FVM;
+  }
+  emit_vex_arith(0xFD, dst, nds, src, VEX_SIMD_66, vector_len);
+}
+
+void Assembler::vpaddd(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_vex_arith(0xFE, dst, nds, src, VEX_SIMD_66, vector_len);
+}
+
+void Assembler::vpaddq(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_64bit;
+    emit_vex_arith_q(0xD4, dst, nds, src, VEX_SIMD_66, vector_len);
+  } else {
+    emit_vex_arith(0xD4, dst, nds, src, VEX_SIMD_66, vector_len);
+  }
 }
 
 void Assembler::psubb(XMMRegister dst, XMMRegister src) {
@@ -3464,84 +4252,149 @@
 
 void Assembler::psubq(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0xFB, dst, src, VEX_SIMD_66);
-}
-
-void Assembler::vpsubb(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xF8, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpsubw(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xF9, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpsubd(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xFA, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpsubq(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xFB, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpsubb(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xF8, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpsubw(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xF9, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpsubd(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xFA, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpsubq(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xFB, dst, nds, src, VEX_SIMD_66, vector256);
+  if (VM_Version::supports_evex()) {
+    emit_simd_arith_q(0xFB, dst, src, VEX_SIMD_66);
+  } else {
+    emit_simd_arith(0xFB, dst, src, VEX_SIMD_66);
+  }
+}
+
+void Assembler::vpsubb(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  emit_vex_arith(0xF8, dst, nds, src, VEX_SIMD_66, vector_len,
+                 (VM_Version::supports_avx512bw() == false));
+}
+
+void Assembler::vpsubw(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  emit_vex_arith(0xF9, dst, nds, src, VEX_SIMD_66, vector_len,
+                 (VM_Version::supports_avx512bw() == false));
+}
+
+void Assembler::vpsubd(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  emit_vex_arith(0xFA, dst, nds, src, VEX_SIMD_66, vector_len);
+}
+
+void Assembler::vpsubq(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  if (VM_Version::supports_evex()) {
+    emit_vex_arith_q(0xFB, dst, nds, src, VEX_SIMD_66, vector_len);
+  } else {
+    emit_vex_arith(0xFB, dst, nds, src, VEX_SIMD_66, vector_len);
+  }
+}
+
+void Assembler::vpsubb(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FVM;
+  }
+  emit_vex_arith(0xF8, dst, nds, src, VEX_SIMD_66, vector_len,
+                 (VM_Version::supports_avx512bw() == false));
+}
+
+void Assembler::vpsubw(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FVM;
+  }
+  emit_vex_arith(0xF9, dst, nds, src, VEX_SIMD_66, vector_len,
+                 (VM_Version::supports_avx512bw() == false));
+}
+
+void Assembler::vpsubd(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_vex_arith(0xFA, dst, nds, src, VEX_SIMD_66, vector_len);
+}
+
+void Assembler::vpsubq(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_64bit;
+    emit_vex_arith_q(0xFB, dst, nds, src, VEX_SIMD_66, vector_len);
+  } else {
+    emit_vex_arith(0xFB, dst, nds, src, VEX_SIMD_66, vector_len);
+  }
 }
 
 void Assembler::pmullw(XMMRegister dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0xD5, dst, src, VEX_SIMD_66);
+  emit_simd_arith(0xD5, dst, src, VEX_SIMD_66,
+                  (VM_Version::supports_avx512bw() == false));
 }
 
 void Assembler::pmulld(XMMRegister dst, XMMRegister src) {
   assert(VM_Version::supports_sse4_1(), "");
-  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_66, VEX_OPCODE_0F_38);
+  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_66,
+                                      false, VEX_OPCODE_0F_38);
+  emit_int8(0x40);
+  emit_int8((unsigned char)(0xC0 | encode));
+}
+
+void Assembler::vpmullw(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  emit_vex_arith(0xD5, dst, nds, src, VEX_SIMD_66, vector_len,
+                 (VM_Version::supports_avx512bw() == false));
+}
+
+void Assembler::vpmulld(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  int encode = vex_prefix_and_encode(dst, nds, src, VEX_SIMD_66,
+                                     vector_len, VEX_OPCODE_0F_38);
   emit_int8(0x40);
   emit_int8((unsigned char)(0xC0 | encode));
 }
 
-void Assembler::vpmullw(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xD5, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpmulld(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  int encode = vex_prefix_and_encode(dst, nds, src, VEX_SIMD_66, vector256, VEX_OPCODE_0F_38);
+void Assembler::vpmullq(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(UseAVX > 2, "requires some form of AVX");
+  int src_enc = src->encoding();
+  int dst_enc = dst->encoding();
+  int nds_enc = nds->is_valid() ? nds->encoding() : 0;
+  int encode = vex_prefix_and_encode(dst_enc, nds_enc, src_enc, VEX_SIMD_66,
+                                     VEX_OPCODE_0F_38, true, vector_len, false, false);
   emit_int8(0x40);
   emit_int8((unsigned char)(0xC0 | encode));
 }
 
-void Assembler::vpmullw(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xD5, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpmulld(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
+void Assembler::vpmullw(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FVM;
+  }
+  emit_vex_arith(0xD5, dst, nds, src, VEX_SIMD_66, vector_len);
+}
+
+void Assembler::vpmulld(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_32bit;
+  }
   InstructionMark im(this);
   int dst_enc = dst->encoding();
   int nds_enc = nds->is_valid() ? nds->encoding() : 0;
-  vex_prefix(src, nds_enc, dst_enc, VEX_SIMD_66, VEX_OPCODE_0F_38, false, vector256);
+  vex_prefix(src, nds_enc, dst_enc, VEX_SIMD_66,
+             VEX_OPCODE_0F_38, false, vector_len);
+  emit_int8(0x40);
+  emit_operand(dst, src);
+}
+
+void Assembler::vpmullq(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_64bit;
+  }
+  InstructionMark im(this);
+  int dst_enc = dst->encoding();
+  int nds_enc = nds->is_valid() ? nds->encoding() : 0;
+  vex_prefix(src, nds_enc, dst_enc, VEX_SIMD_66, VEX_OPCODE_0F_38, true, vector_len);
   emit_int8(0x40);
   emit_operand(dst, src);
 }
@@ -3550,7 +4403,8 @@
 void Assembler::psllw(XMMRegister dst, int shift) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
   // XMM6 is for /6 encoding: 66 0F 71 /6 ib
-  int encode = simd_prefix_and_encode(xmm6, dst, dst, VEX_SIMD_66);
+  int encode = simd_prefix_and_encode(xmm6, dst, dst, VEX_SIMD_66, false, VEX_OPCODE_0F,
+                                      false, AVX_128bit, (VM_Version::supports_avx512bw() == false));
   emit_int8(0x71);
   emit_int8((unsigned char)(0xC0 | encode));
   emit_int8(shift & 0xFF);
@@ -3559,7 +4413,7 @@
 void Assembler::pslld(XMMRegister dst, int shift) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
   // XMM6 is for /6 encoding: 66 0F 72 /6 ib
-  int encode = simd_prefix_and_encode(xmm6, dst, dst, VEX_SIMD_66);
+  int encode = simd_prefix_and_encode(xmm6, dst, dst, VEX_SIMD_66, false);
   emit_int8(0x72);
   emit_int8((unsigned char)(0xC0 | encode));
   emit_int8(shift & 0xFF);
@@ -3568,7 +4422,7 @@
 void Assembler::psllq(XMMRegister dst, int shift) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
   // XMM6 is for /6 encoding: 66 0F 73 /6 ib
-  int encode = simd_prefix_and_encode(xmm6, dst, dst, VEX_SIMD_66);
+  int encode = simd_prefix_and_encode(xmm6, dst, dst, VEX_SIMD_66, false, VEX_OPCODE_0F, true);
   emit_int8(0x73);
   emit_int8((unsigned char)(0xC0 | encode));
   emit_int8(shift & 0xFF);
@@ -3576,7 +4430,8 @@
 
 void Assembler::psllw(XMMRegister dst, XMMRegister shift) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0xF1, dst, shift, VEX_SIMD_66);
+  emit_simd_arith(0xF1, dst, shift, VEX_SIMD_66, false,
+                  (VM_Version::supports_avx512bw() == false));
 }
 
 void Assembler::pslld(XMMRegister dst, XMMRegister shift) {
@@ -3586,50 +4441,65 @@
 
 void Assembler::psllq(XMMRegister dst, XMMRegister shift) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0xF3, dst, shift, VEX_SIMD_66);
-}
-
-void Assembler::vpsllw(XMMRegister dst, XMMRegister src, int shift, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
+  if (VM_Version::supports_evex()) {
+    emit_simd_arith_q(0xF3, dst, shift, VEX_SIMD_66);
+  } else {
+    emit_simd_arith(0xF3, dst, shift, VEX_SIMD_66);
+  }
+}
+
+void Assembler::vpsllw(XMMRegister dst, XMMRegister src, int shift, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
   // XMM6 is for /6 encoding: 66 0F 71 /6 ib
-  emit_vex_arith(0x71, xmm6, dst, src, VEX_SIMD_66, vector256);
+  emit_vex_arith(0x71, xmm6, dst, src, VEX_SIMD_66, vector_len,
+                 (VM_Version::supports_avx512bw() == false));
   emit_int8(shift & 0xFF);
 }
 
-void Assembler::vpslld(XMMRegister dst, XMMRegister src, int shift, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
+void Assembler::vpslld(XMMRegister dst, XMMRegister src, int shift, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
   // XMM6 is for /6 encoding: 66 0F 72 /6 ib
-  emit_vex_arith(0x72, xmm6, dst, src, VEX_SIMD_66, vector256);
+  emit_vex_arith(0x72, xmm6, dst, src, VEX_SIMD_66, vector_len);
   emit_int8(shift & 0xFF);
 }
 
-void Assembler::vpsllq(XMMRegister dst, XMMRegister src, int shift, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
+void Assembler::vpsllq(XMMRegister dst, XMMRegister src, int shift, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
   // XMM6 is for /6 encoding: 66 0F 73 /6 ib
-  emit_vex_arith(0x73, xmm6, dst, src, VEX_SIMD_66, vector256);
+  if (VM_Version::supports_evex()) {
+    emit_vex_arith_q(0x73, xmm6, dst, src, VEX_SIMD_66, vector_len);
+  } else {
+    emit_vex_arith(0x73, xmm6, dst, src, VEX_SIMD_66, vector_len);
+  }
   emit_int8(shift & 0xFF);
 }
 
-void Assembler::vpsllw(XMMRegister dst, XMMRegister src, XMMRegister shift, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xF1, dst, src, shift, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpslld(XMMRegister dst, XMMRegister src, XMMRegister shift, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xF2, dst, src, shift, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpsllq(XMMRegister dst, XMMRegister src, XMMRegister shift, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xF3, dst, src, shift, VEX_SIMD_66, vector256);
+void Assembler::vpsllw(XMMRegister dst, XMMRegister src, XMMRegister shift, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  emit_vex_arith(0xF1, dst, src, shift, VEX_SIMD_66, vector_len,
+                 (VM_Version::supports_avx512bw() == false));
+}
+
+void Assembler::vpslld(XMMRegister dst, XMMRegister src, XMMRegister shift, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  emit_vex_arith(0xF2, dst, src, shift, VEX_SIMD_66, vector_len);
+}
+
+void Assembler::vpsllq(XMMRegister dst, XMMRegister src, XMMRegister shift, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  if (VM_Version::supports_evex()) {
+    emit_vex_arith_q(0xF3, dst, src, shift, VEX_SIMD_66, vector_len);
+  } else {
+    emit_vex_arith(0xF3, dst, src, shift, VEX_SIMD_66, vector_len);
+  }
 }
 
 // Shift packed integers logically right by specified number of bits.
 void Assembler::psrlw(XMMRegister dst, int shift) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
   // XMM2 is for /2 encoding: 66 0F 71 /2 ib
-  int encode = simd_prefix_and_encode(xmm2, dst, dst, VEX_SIMD_66);
+  int encode = simd_prefix_and_encode(xmm2, dst, dst, VEX_SIMD_66, false, VEX_OPCODE_0F,
+                                      (VM_Version::supports_avx512bw() == false));
   emit_int8(0x71);
   emit_int8((unsigned char)(0xC0 | encode));
   emit_int8(shift & 0xFF);
@@ -3638,7 +4508,7 @@
 void Assembler::psrld(XMMRegister dst, int shift) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
   // XMM2 is for /2 encoding: 66 0F 72 /2 ib
-  int encode = simd_prefix_and_encode(xmm2, dst, dst, VEX_SIMD_66);
+  int encode = simd_prefix_and_encode(xmm2, dst, dst, VEX_SIMD_66, false);
   emit_int8(0x72);
   emit_int8((unsigned char)(0xC0 | encode));
   emit_int8(shift & 0xFF);
@@ -3649,7 +4519,12 @@
   // shifts 128 bit value in xmm register by number of bytes.
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
   // XMM2 is for /2 encoding: 66 0F 73 /2 ib
-  int encode = simd_prefix_and_encode(xmm2, dst, dst, VEX_SIMD_66);
+  int encode = 0;
+  if (VM_Version::supports_evex() && VM_Version::supports_avx512bw()) {
+    encode = simd_prefix_and_encode(xmm2, dst, dst, VEX_SIMD_66, true, VEX_OPCODE_0F, false);
+  } else {
+    encode = simd_prefix_and_encode(xmm2, dst, dst, VEX_SIMD_66, false, VEX_OPCODE_0F, true);
+  }
   emit_int8(0x73);
   emit_int8((unsigned char)(0xC0 | encode));
   emit_int8(shift & 0xFF);
@@ -3657,7 +4532,8 @@
 
 void Assembler::psrlw(XMMRegister dst, XMMRegister shift) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0xD1, dst, shift, VEX_SIMD_66);
+  emit_simd_arith(0xD1, dst, shift, VEX_SIMD_66, false,
+                  (VM_Version::supports_avx512bw() == false));
 }
 
 void Assembler::psrld(XMMRegister dst, XMMRegister shift) {
@@ -3667,50 +4543,65 @@
 
 void Assembler::psrlq(XMMRegister dst, XMMRegister shift) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0xD3, dst, shift, VEX_SIMD_66);
-}
-
-void Assembler::vpsrlw(XMMRegister dst, XMMRegister src, int shift, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
+  if (VM_Version::supports_evex()) {
+    emit_simd_arith_q(0xD3, dst, shift, VEX_SIMD_66);
+  } else {
+    emit_simd_arith(0xD3, dst, shift, VEX_SIMD_66);
+  }
+}
+
+void Assembler::vpsrlw(XMMRegister dst, XMMRegister src, int shift, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
   // XMM2 is for /2 encoding: 66 0F 73 /2 ib
-  emit_vex_arith(0x71, xmm2, dst, src, VEX_SIMD_66, vector256);
+  emit_vex_arith(0x71, xmm2, dst, src, VEX_SIMD_66, vector_len,
+                 (VM_Version::supports_avx512bw() == false));
   emit_int8(shift & 0xFF);
 }
 
-void Assembler::vpsrld(XMMRegister dst, XMMRegister src, int shift, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
+void Assembler::vpsrld(XMMRegister dst, XMMRegister src, int shift, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
   // XMM2 is for /2 encoding: 66 0F 73 /2 ib
-  emit_vex_arith(0x72, xmm2, dst, src, VEX_SIMD_66, vector256);
+  emit_vex_arith(0x72, xmm2, dst, src, VEX_SIMD_66, vector_len);
   emit_int8(shift & 0xFF);
 }
 
-void Assembler::vpsrlq(XMMRegister dst, XMMRegister src, int shift, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
+void Assembler::vpsrlq(XMMRegister dst, XMMRegister src, int shift, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
   // XMM2 is for /2 encoding: 66 0F 73 /2 ib
-  emit_vex_arith(0x73, xmm2, dst, src, VEX_SIMD_66, vector256);
+  if (VM_Version::supports_evex()) {
+    emit_vex_arith_q(0x73, xmm2, dst, src, VEX_SIMD_66, vector_len);
+  } else {
+    emit_vex_arith(0x73, xmm2, dst, src, VEX_SIMD_66, vector_len);
+  }
   emit_int8(shift & 0xFF);
 }
 
-void Assembler::vpsrlw(XMMRegister dst, XMMRegister src, XMMRegister shift, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xD1, dst, src, shift, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpsrld(XMMRegister dst, XMMRegister src, XMMRegister shift, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xD2, dst, src, shift, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpsrlq(XMMRegister dst, XMMRegister src, XMMRegister shift, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xD3, dst, src, shift, VEX_SIMD_66, vector256);
+void Assembler::vpsrlw(XMMRegister dst, XMMRegister src, XMMRegister shift, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  emit_vex_arith(0xD1, dst, src, shift, VEX_SIMD_66, vector_len,
+                 (VM_Version::supports_avx512bw() == false));
+}
+
+void Assembler::vpsrld(XMMRegister dst, XMMRegister src, XMMRegister shift, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  emit_vex_arith(0xD2, dst, src, shift, VEX_SIMD_66, vector_len);
+}
+
+void Assembler::vpsrlq(XMMRegister dst, XMMRegister src, XMMRegister shift, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  if (VM_Version::supports_evex()) {
+    emit_vex_arith_q(0xD3, dst, src, shift, VEX_SIMD_66, vector_len);
+  } else {
+    emit_vex_arith(0xD3, dst, src, shift, VEX_SIMD_66, vector_len);
+  }
 }
 
 // Shift packed integers arithmetically right by specified number of bits.
 void Assembler::psraw(XMMRegister dst, int shift) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
   // XMM4 is for /4 encoding: 66 0F 71 /4 ib
-  int encode = simd_prefix_and_encode(xmm4, dst, dst, VEX_SIMD_66);
+  int encode = simd_prefix_and_encode(xmm4, dst, dst, VEX_SIMD_66, false, VEX_OPCODE_0F,
+                                      (VM_Version::supports_avx512bw() == false));
   emit_int8(0x71);
   emit_int8((unsigned char)(0xC0 | encode));
   emit_int8(shift & 0xFF);
@@ -3719,7 +4610,7 @@
 void Assembler::psrad(XMMRegister dst, int shift) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
   // XMM4 is for /4 encoding: 66 0F 72 /4 ib
-  int encode = simd_prefix_and_encode(xmm4, dst, dst, VEX_SIMD_66);
+  int encode = simd_prefix_and_encode(xmm4, dst, dst, VEX_SIMD_66, false);
   emit_int8(0x72);
   emit_int8((unsigned char)(0xC0 | encode));
   emit_int8(shift & 0xFF);
@@ -3727,7 +4618,8 @@
 
 void Assembler::psraw(XMMRegister dst, XMMRegister shift) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  emit_simd_arith(0xE1, dst, shift, VEX_SIMD_66);
+  emit_simd_arith(0xE1, dst, shift, VEX_SIMD_66,
+                  (VM_Version::supports_avx512bw() == false));
 }
 
 void Assembler::psrad(XMMRegister dst, XMMRegister shift) {
@@ -3735,28 +4627,30 @@
   emit_simd_arith(0xE2, dst, shift, VEX_SIMD_66);
 }
 
-void Assembler::vpsraw(XMMRegister dst, XMMRegister src, int shift, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
+void Assembler::vpsraw(XMMRegister dst, XMMRegister src, int shift, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
   // XMM4 is for /4 encoding: 66 0F 71 /4 ib
-  emit_vex_arith(0x71, xmm4, dst, src, VEX_SIMD_66, vector256);
+  emit_vex_arith(0x71, xmm4, dst, src, VEX_SIMD_66, vector_len,
+                 (VM_Version::supports_avx512bw() == false));
   emit_int8(shift & 0xFF);
 }
 
-void Assembler::vpsrad(XMMRegister dst, XMMRegister src, int shift, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
+void Assembler::vpsrad(XMMRegister dst, XMMRegister src, int shift, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
   // XMM4 is for /4 encoding: 66 0F 71 /4 ib
-  emit_vex_arith(0x72, xmm4, dst, src, VEX_SIMD_66, vector256);
+  emit_vex_arith(0x72, xmm4, dst, src, VEX_SIMD_66, vector_len);
   emit_int8(shift & 0xFF);
 }
 
-void Assembler::vpsraw(XMMRegister dst, XMMRegister src, XMMRegister shift, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xE1, dst, src, shift, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpsrad(XMMRegister dst, XMMRegister src, XMMRegister shift, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xE2, dst, src, shift, VEX_SIMD_66, vector256);
+void Assembler::vpsraw(XMMRegister dst, XMMRegister src, XMMRegister shift, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  emit_vex_arith(0xE1, dst, src, shift, VEX_SIMD_66, vector_len,
+                 (VM_Version::supports_avx512bw() == false));
+}
+
+void Assembler::vpsrad(XMMRegister dst, XMMRegister src, XMMRegister shift, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  emit_vex_arith(0xE2, dst, src, shift, VEX_SIMD_66, vector_len);
 }
 
 
@@ -3766,14 +4660,18 @@
   emit_simd_arith(0xDB, dst, src, VEX_SIMD_66);
 }
 
-void Assembler::vpand(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xDB, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpand(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xDB, dst, nds, src, VEX_SIMD_66, vector256);
+void Assembler::vpand(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  emit_vex_arith(0xDB, dst, nds, src, VEX_SIMD_66, vector_len);
+}
+
+void Assembler::vpand(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_vex_arith(0xDB, dst, nds, src, VEX_SIMD_66, vector_len);
 }
 
 void Assembler::por(XMMRegister dst, XMMRegister src) {
@@ -3781,14 +4679,18 @@
   emit_simd_arith(0xEB, dst, src, VEX_SIMD_66);
 }
 
-void Assembler::vpor(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xEB, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpor(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xEB, dst, nds, src, VEX_SIMD_66, vector256);
+void Assembler::vpor(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  emit_vex_arith(0xEB, dst, nds, src, VEX_SIMD_66, vector_len);
+}
+
+void Assembler::vpor(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_vex_arith(0xEB, dst, nds, src, VEX_SIMD_66, vector_len);
 }
 
 void Assembler::pxor(XMMRegister dst, XMMRegister src) {
@@ -3796,21 +4698,25 @@
   emit_simd_arith(0xEF, dst, src, VEX_SIMD_66);
 }
 
-void Assembler::vpxor(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xEF, dst, nds, src, VEX_SIMD_66, vector256);
-}
-
-void Assembler::vpxor(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
-  assert(VM_Version::supports_avx() && !vector256 || VM_Version::supports_avx2(), "256 bit integer vectors requires AVX2");
-  emit_vex_arith(0xEF, dst, nds, src, VEX_SIMD_66, vector256);
+void Assembler::vpxor(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  emit_vex_arith(0xEF, dst, nds, src, VEX_SIMD_66, vector_len);
+}
+
+void Assembler::vpxor(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
+  assert(UseAVX > 0, "requires some form of AVX");
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_FV;
+    input_size_in_bits = EVEX_32bit;
+  }
+  emit_vex_arith(0xEF, dst, nds, src, VEX_SIMD_66, vector_len);
 }
 
 
 void Assembler::vinsertf128h(XMMRegister dst, XMMRegister nds, XMMRegister src) {
   assert(VM_Version::supports_avx(), "");
-  bool vector256 = true;
-  int encode = vex_prefix_and_encode(dst, nds, src, VEX_SIMD_66, vector256, VEX_OPCODE_0F_3A);
+  int vector_len = AVX_256bit;
+  int encode = vex_prefix_and_encode(dst, nds, src, VEX_SIMD_66, vector_len, VEX_OPCODE_0F_3A);
   emit_int8(0x18);
   emit_int8((unsigned char)(0xC0 | encode));
   // 0x00 - insert into lower 128 bits
@@ -3818,14 +4724,51 @@
   emit_int8(0x01);
 }
 
+void Assembler::vinsertf64x4h(XMMRegister dst, XMMRegister nds, XMMRegister src) {
+  assert(VM_Version::supports_evex(), "");
+  int vector_len = AVX_512bit;
+  int src_enc = src->encoding();
+  int dst_enc = dst->encoding();
+  int nds_enc = nds->is_valid() ? nds->encoding() : 0;
+  int encode = vex_prefix_and_encode(dst_enc, nds_enc, src_enc, VEX_SIMD_66,
+                                     VEX_OPCODE_0F_3A, true, vector_len, false, false);
+  emit_int8(0x1A);
+  emit_int8((unsigned char)(0xC0 | encode));
+  // 0x00 - insert into lower 256 bits
+  // 0x01 - insert into upper 256 bits
+  emit_int8(0x01);
+}
+
+void Assembler::vinsertf64x4h(XMMRegister dst, Address src) {
+  assert(VM_Version::supports_avx(), "");
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T4;
+    input_size_in_bits = EVEX_64bit;
+  }
+  InstructionMark im(this);
+  int vector_len = AVX_512bit;
+  assert(dst != xnoreg, "sanity");
+  int dst_enc = dst->encoding();
+  // swap src<->dst for encoding
+  vex_prefix(src, dst_enc, dst_enc, VEX_SIMD_66, VEX_OPCODE_0F_3A, true, vector_len);
+  emit_int8(0x1A);
+  emit_operand(dst, src);
+  // 0x01 - insert into upper 128 bits
+  emit_int8(0x01);
+}
+
 void Assembler::vinsertf128h(XMMRegister dst, Address src) {
   assert(VM_Version::supports_avx(), "");
-  InstructionMark im(this);
-  bool vector256 = true;
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T4;
+    input_size_in_bits = EVEX_32bit;
+  }
+  InstructionMark im(this);
+  int vector_len = AVX_256bit;
   assert(dst != xnoreg, "sanity");
   int dst_enc = dst->encoding();
   // swap src<->dst for encoding
-  vex_prefix(src, dst_enc, dst_enc, VEX_SIMD_66, VEX_OPCODE_0F_3A, false, vector256);
+  vex_prefix(src, dst_enc, dst_enc, VEX_SIMD_66, VEX_OPCODE_0F_3A, false, vector_len);
   emit_int8(0x18);
   emit_operand(dst, src);
   // 0x01 - insert into upper 128 bits
@@ -3834,8 +4777,8 @@
 
 void Assembler::vextractf128h(XMMRegister dst, XMMRegister src) {
   assert(VM_Version::supports_avx(), "");
-  bool vector256 = true;
-  int encode = vex_prefix_and_encode(src, xnoreg, dst, VEX_SIMD_66, vector256, VEX_OPCODE_0F_3A);
+  int vector_len = AVX_256bit;
+  int encode = vex_prefix_and_encode(src, xnoreg, dst, VEX_SIMD_66, vector_len, VEX_OPCODE_0F_3A);
   emit_int8(0x19);
   emit_int8((unsigned char)(0xC0 | encode));
   // 0x00 - insert into lower 128 bits
@@ -3845,11 +4788,15 @@
 
 void Assembler::vextractf128h(Address dst, XMMRegister src) {
   assert(VM_Version::supports_avx(), "");
-  InstructionMark im(this);
-  bool vector256 = true;
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T4;
+    input_size_in_bits = EVEX_32bit;
+  }
+  InstructionMark im(this);
+  int vector_len = AVX_256bit;
   assert(src != xnoreg, "sanity");
   int src_enc = src->encoding();
-  vex_prefix(dst, 0, src_enc, VEX_SIMD_66, VEX_OPCODE_0F_3A, false, vector256);
+  vex_prefix(dst, 0, src_enc, VEX_SIMD_66, VEX_OPCODE_0F_3A, false, vector_len);
   emit_int8(0x19);
   emit_operand(src, dst);
   // 0x01 - extract from upper 128 bits
@@ -3858,8 +4805,8 @@
 
 void Assembler::vinserti128h(XMMRegister dst, XMMRegister nds, XMMRegister src) {
   assert(VM_Version::supports_avx2(), "");
-  bool vector256 = true;
-  int encode = vex_prefix_and_encode(dst, nds, src, VEX_SIMD_66, vector256, VEX_OPCODE_0F_3A);
+  int vector_len = AVX_256bit;
+  int encode = vex_prefix_and_encode(dst, nds, src, VEX_SIMD_66, vector_len, VEX_OPCODE_0F_3A);
   emit_int8(0x38);
   emit_int8((unsigned char)(0xC0 | encode));
   // 0x00 - insert into lower 128 bits
@@ -3867,38 +4814,169 @@
   emit_int8(0x01);
 }
 
+void Assembler::vinserti64x4h(XMMRegister dst, XMMRegister nds, XMMRegister src) {
+  assert(VM_Version::supports_evex(), "");
+  int vector_len = AVX_512bit;
+  int src_enc = src->encoding();
+  int dst_enc = dst->encoding();
+  int nds_enc = nds->is_valid() ? nds->encoding() : 0;
+  int encode = vex_prefix_and_encode(dst_enc, nds_enc, src_enc, VEX_SIMD_66, VEX_OPCODE_0F_3A,
+                                     VM_Version::supports_avx512dq(), vector_len, false, false);
+  emit_int8(0x38);
+  emit_int8((unsigned char)(0xC0 | encode));
+  // 0x00 - insert into lower 256 bits
+  // 0x01 - insert into upper 256 bits
+  emit_int8(0x01);
+}
+
 void Assembler::vinserti128h(XMMRegister dst, Address src) {
   assert(VM_Version::supports_avx2(), "");
-  InstructionMark im(this);
-  bool vector256 = true;
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T4;
+    input_size_in_bits = EVEX_32bit;
+  }
+  InstructionMark im(this);
+  int vector_len = AVX_256bit;
   assert(dst != xnoreg, "sanity");
   int dst_enc = dst->encoding();
   // swap src<->dst for encoding
-  vex_prefix(src, dst_enc, dst_enc, VEX_SIMD_66, VEX_OPCODE_0F_3A, false, vector256);
+  vex_prefix(src, dst_enc, dst_enc, VEX_SIMD_66, VEX_OPCODE_0F_3A, false, vector_len);
   emit_int8(0x38);
   emit_operand(dst, src);
   // 0x01 - insert into upper 128 bits
   emit_int8(0x01);
 }
 
+void Assembler::vextracti128h(XMMRegister dst, XMMRegister src) {
+  assert(VM_Version::supports_avx(), "");
+  int vector_len = AVX_256bit;
+  int encode = vex_prefix_and_encode(src, xnoreg, dst, VEX_SIMD_66, vector_len, VEX_OPCODE_0F_3A);
+  emit_int8(0x39);
+  emit_int8((unsigned char)(0xC0 | encode));
+  // 0x00 - insert into lower 128 bits
+  // 0x01 - insert into upper 128 bits
+  emit_int8(0x01);
+}
+
 void Assembler::vextracti128h(Address dst, XMMRegister src) {
   assert(VM_Version::supports_avx2(), "");
-  InstructionMark im(this);
-  bool vector256 = true;
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T4;
+    input_size_in_bits = EVEX_32bit;
+  }
+  InstructionMark im(this);
+  int vector_len = AVX_256bit;
   assert(src != xnoreg, "sanity");
   int src_enc = src->encoding();
-  vex_prefix(dst, 0, src_enc, VEX_SIMD_66, VEX_OPCODE_0F_3A, false, vector256);
+  vex_prefix(dst, 0, src_enc, VEX_SIMD_66, VEX_OPCODE_0F_3A, false, vector_len);
   emit_int8(0x39);
   emit_operand(src, dst);
   // 0x01 - extract from upper 128 bits
   emit_int8(0x01);
 }
 
+void Assembler::vextracti64x4h(XMMRegister dst, XMMRegister src) {
+  assert(VM_Version::supports_evex(), "");
+  int vector_len = AVX_512bit;
+  int src_enc = src->encoding();
+  int dst_enc = dst->encoding();
+  int encode = vex_prefix_and_encode(src_enc, 0, dst_enc, VEX_SIMD_66, VEX_OPCODE_0F_3A,
+                                     true, vector_len, false, false);
+  emit_int8(0x3B);
+  emit_int8((unsigned char)(0xC0 | encode));
+  // 0x01 - extract from upper 256 bits
+  emit_int8(0x01);
+}
+
+void Assembler::vextracti64x2h(XMMRegister dst, XMMRegister src, int value) {
+  assert(VM_Version::supports_evex(), "");
+  int vector_len = AVX_512bit;
+  int src_enc = src->encoding();
+  int dst_enc = dst->encoding();
+  int encode = vex_prefix_and_encode(src_enc, 0, dst_enc, VEX_SIMD_66, VEX_OPCODE_0F_3A,
+                                     VM_Version::supports_avx512dq(), vector_len, false, false);
+  emit_int8(0x39);
+  emit_int8((unsigned char)(0xC0 | encode));
+  // 0x01 - extract from bits 255:128
+  // 0x02 - extract from bits 383:256
+  // 0x03 - extract from bits 511:384
+  emit_int8(value & 0x3);
+}
+
+void Assembler::vextractf64x4h(XMMRegister dst, XMMRegister src) {
+  assert(VM_Version::supports_evex(), "");
+  int vector_len = AVX_512bit;
+  int src_enc = src->encoding();
+  int dst_enc = dst->encoding();
+  int encode = vex_prefix_and_encode(src_enc, 0, dst_enc, VEX_SIMD_66, VEX_OPCODE_0F_3A,
+                                     VM_Version::supports_avx512dq(), vector_len, false, false);
+  emit_int8(0x1B);
+  emit_int8((unsigned char)(0xC0 | encode));
+  // 0x01 - extract from upper 256 bits
+  emit_int8(0x01);
+}
+
+void Assembler::vextractf64x4h(Address dst, XMMRegister src) {
+  assert(VM_Version::supports_avx2(), "");
+  tuple_type = EVEX_T4;
+  input_size_in_bits = EVEX_64bit;
+  InstructionMark im(this);
+  int vector_len = AVX_512bit;
+  assert(src != xnoreg, "sanity");
+  int src_enc = src->encoding();
+  vex_prefix(dst, 0, src_enc, VEX_SIMD_66, VEX_OPCODE_0F_3A,
+             VM_Version::supports_avx512dq(), vector_len);
+  emit_int8(0x1B);
+  emit_operand(src, dst);
+  // 0x01 - extract from upper 128 bits
+  emit_int8(0x01);
+}
+
+void Assembler::vextractf32x4h(XMMRegister dst, XMMRegister src, int value) {
+  assert(VM_Version::supports_evex(), "");
+  int vector_len = AVX_512bit;
+  int src_enc = src->encoding();
+  int dst_enc = dst->encoding();
+  int encode = vex_prefix_and_encode(src_enc, 0, dst_enc, VEX_SIMD_66,
+                                     VEX_OPCODE_0F_3A, false, vector_len, false, false);
+  emit_int8(0x19);
+  emit_int8((unsigned char)(0xC0 | encode));
+  // 0x01 - extract from bits 255:128
+  // 0x02 - extract from bits 383:256
+  // 0x03 - extract from bits 511:384
+  emit_int8(value & 0x3);
+}
+
+void Assembler::vextractf64x2h(XMMRegister dst, XMMRegister src, int value) {
+  assert(VM_Version::supports_evex(), "");
+  int vector_len = AVX_512bit;
+  int src_enc = src->encoding();
+  int dst_enc = dst->encoding();
+  int encode = vex_prefix_and_encode(src_enc, 0, dst_enc, VEX_SIMD_66, VEX_OPCODE_0F_3A,
+                                     VM_Version::supports_avx512dq(), vector_len, false, false);
+  emit_int8(0x19);
+  emit_int8((unsigned char)(0xC0 | encode));
+  // 0x01 - extract from bits 255:128
+  // 0x02 - extract from bits 383:256
+  // 0x03 - extract from bits 511:384
+  emit_int8(value & 0x3);
+}
+
 // duplicate 4-bytes integer data from src into 8 locations in dest
 void Assembler::vpbroadcastd(XMMRegister dst, XMMRegister src) {
   assert(VM_Version::supports_avx2(), "");
-  bool vector256 = true;
-  int encode = vex_prefix_and_encode(dst, xnoreg, src, VEX_SIMD_66, vector256, VEX_OPCODE_0F_38);
+  int vector_len = AVX_256bit;
+  int encode = vex_prefix_and_encode(dst, xnoreg, src, VEX_SIMD_66,
+                                     vector_len, VEX_OPCODE_0F_38, false);
+  emit_int8(0x58);
+  emit_int8((unsigned char)(0xC0 | encode));
+}
+
+// duplicate 4-bytes integer data from src into 8 locations in dest
+void Assembler::evpbroadcastd(XMMRegister dst, XMMRegister src, int vector_len) {
+  assert(VM_Version::supports_evex(), "");
+  int encode = vex_prefix_and_encode(dst, xnoreg, src, VEX_SIMD_66,
+                                     vector_len, VEX_OPCODE_0F_38, false);
   emit_int8(0x58);
   emit_int8((unsigned char)(0xC0 | encode));
 }
@@ -3906,7 +4984,8 @@
 // Carry-Less Multiplication Quadword
 void Assembler::pclmulqdq(XMMRegister dst, XMMRegister src, int mask) {
   assert(VM_Version::supports_clmul(), "");
-  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_66, VEX_OPCODE_0F_3A);
+  int encode = simd_prefix_and_encode(dst, dst, src, VEX_SIMD_66, false,
+                                      VEX_OPCODE_0F_3A, false, AVX_128bit, true);
   emit_int8(0x44);
   emit_int8((unsigned char)(0xC0 | encode));
   emit_int8((unsigned char)mask);
@@ -3915,8 +4994,9 @@
 // Carry-Less Multiplication Quadword
 void Assembler::vpclmulqdq(XMMRegister dst, XMMRegister nds, XMMRegister src, int mask) {
   assert(VM_Version::supports_avx() && VM_Version::supports_clmul(), "");
-  bool vector256 = false;
-  int encode = vex_prefix_and_encode(dst, nds, src, VEX_SIMD_66, vector256, VEX_OPCODE_0F_3A);
+  int vector_len = AVX_128bit;
+  int encode = vex_prefix_and_encode(dst, nds, src, VEX_SIMD_66,
+                                     vector_len, VEX_OPCODE_0F_3A, true);
   emit_int8(0x44);
   emit_int8((unsigned char)(0xC0 | encode));
   emit_int8((unsigned char)mask);
@@ -3924,8 +5004,11 @@
 
 void Assembler::vzeroupper() {
   assert(VM_Version::supports_avx(), "");
-  (void)vex_prefix_and_encode(xmm0, xmm0, xmm0, VEX_SIMD_NONE);
-  emit_int8(0x77);
+  if (UseAVX < 3)
+  {
+    (void)vex_prefix_and_encode(xmm0, xmm0, xmm0, VEX_SIMD_NONE);
+    emit_int8(0x77);
+  }
 }
 
 
@@ -4442,7 +5525,7 @@
 }
 
 
-void Assembler::vex_prefix(bool vex_r, bool vex_b, bool vex_x, bool vex_w, int nds_enc, VexSimdPrefix pre, VexOpcode opc, bool vector256) {
+void Assembler::vex_prefix(bool vex_r, bool vex_b, bool vex_x, bool vex_w, int nds_enc, VexSimdPrefix pre, VexOpcode opc, int vector_len) {
   if (vex_b || vex_x || vex_w || (opc == VEX_OPCODE_0F_38) || (opc == VEX_OPCODE_0F_3A)) {
     prefix(VEX_3bytes);
 
@@ -4452,7 +5535,7 @@
     emit_int8(byte1);
 
     int byte2 = ((~nds_enc) & 0xf) << 3;
-    byte2 |= (vex_w ? VEX_W : 0) | (vector256 ? 4 : 0) | pre;
+    byte2 |= (vex_w ? VEX_W : 0) | ((vector_len > 0) ? 4 : 0) | pre;
     emit_int8(byte2);
   } else {
     prefix(VEX_2bytes);
@@ -4460,89 +5543,237 @@
     int byte1 = vex_r ? VEX_R : 0;
     byte1 = (~byte1) & 0x80;
     byte1 |= ((~nds_enc) & 0xf) << 3;
-    byte1 |= (vector256 ? 4 : 0) | pre;
+    byte1 |= ((vector_len > 0 ) ? 4 : 0) | pre;
     emit_int8(byte1);
   }
 }
 
-void Assembler::vex_prefix(Address adr, int nds_enc, int xreg_enc, VexSimdPrefix pre, VexOpcode opc, bool vex_w, bool vector256){
+// This is a 4 byte encoding
+void Assembler::evex_prefix(bool vex_r, bool vex_b, bool vex_x, bool vex_w, bool evex_r, bool evex_v,
+                            int nds_enc, VexSimdPrefix pre, VexOpcode opc,
+                            bool is_extended_context, bool is_merge_context,
+                            int vector_len, bool no_mask_reg ){
+  // EVEX 0x62 prefix
+  prefix(EVEX_4bytes);
+  evex_encoding = (vex_w ? VEX_W : 0) | (evex_r ? EVEX_Rb : 0);
+
+  // P0: byte 2, initialized to RXBR`00mm
+  // instead of not'd
+  int byte2 = (vex_r ? VEX_R : 0) | (vex_x ? VEX_X : 0) | (vex_b ? VEX_B : 0) | (evex_r ? EVEX_Rb : 0);
+  byte2 = (~byte2) & 0xF0;
+  // confine opc opcode extensions in mm bits to lower two bits
+  // of form {0F, 0F_38, 0F_3A}
+  byte2 |= opc;
+  emit_int8(byte2);
+
+  // P1: byte 3 as Wvvvv1pp
+  int byte3 = ((~nds_enc) & 0xf) << 3;
+  // p[10] is always 1
+  byte3 |= EVEX_F;
+  byte3 |= (vex_w & 1) << 7;
+  // confine pre opcode extensions in pp bits to lower two bits
+  // of form {66, F3, F2}
+  byte3 |= pre;
+  emit_int8(byte3);
+
+  // P2: byte 4 as zL'Lbv'aaa
+  int byte4 = (no_mask_reg) ? 0 : 1; // kregs are implemented in the low 3 bits as aaa (hard code k1, it will be initialized for now)
+  // EVEX.v` for extending EVEX.vvvv or VIDX
+  byte4 |= (evex_v ? 0: EVEX_V);
+  // third EXEC.b for broadcast actions
+  byte4 |= (is_extended_context ? EVEX_Rb : 0);
+  // fourth EVEX.L'L for vector length : 0 is 128, 1 is 256, 2 is 512, currently we do not support 1024
+  byte4 |= ((vector_len) & 0x3) << 5;
+  // last is EVEX.z for zero/merge actions
+  byte4 |= (is_merge_context ? EVEX_Z : 0);
+  emit_int8(byte4);
+}
+
+void Assembler::vex_prefix(Address adr, int nds_enc, int xreg_enc, VexSimdPrefix pre,
+                           VexOpcode opc, bool vex_w, int vector_len, bool legacy_mode, bool no_mask_reg) {
   bool vex_r = (xreg_enc >= 8);
   bool vex_b = adr.base_needs_rex();
   bool vex_x = adr.index_needs_rex();
-  vex_prefix(vex_r, vex_b, vex_x, vex_w, nds_enc, pre, opc, vector256);
-}
-
-int Assembler::vex_prefix_and_encode(int dst_enc, int nds_enc, int src_enc, VexSimdPrefix pre, VexOpcode opc, bool vex_w, bool vector256) {
+  avx_vector_len = vector_len;
+
+  // if vector length is turned off, revert to AVX for vectors smaller than AVX_512bit
+  if (VM_Version::supports_avx512vl() == false) {
+    switch (vector_len) {
+    case AVX_128bit:
+    case AVX_256bit:
+      legacy_mode = true;
+      break;
+    }
+  }
+
+  if ((UseAVX > 2) && (legacy_mode == false))
+  {
+    bool evex_r = (xreg_enc >= 16);
+    bool evex_v = (nds_enc >= 16);
+    is_evex_instruction = true;
+    evex_prefix(vex_r, vex_b, vex_x, vex_w, evex_r, evex_v, nds_enc, pre, opc, false, false, vector_len, no_mask_reg);
+  } else {
+    vex_prefix(vex_r, vex_b, vex_x, vex_w, nds_enc, pre, opc, vector_len);
+  }
+}
+
+int Assembler::vex_prefix_and_encode(int dst_enc, int nds_enc, int src_enc, VexSimdPrefix pre, VexOpcode opc,
+                                     bool vex_w, int vector_len, bool legacy_mode, bool no_mask_reg ) {
   bool vex_r = (dst_enc >= 8);
   bool vex_b = (src_enc >= 8);
   bool vex_x = false;
-  vex_prefix(vex_r, vex_b, vex_x, vex_w, nds_enc, pre, opc, vector256);
+  avx_vector_len = vector_len;
+
+  // if vector length is turned off, revert to AVX for vectors smaller than AVX_512bit
+  if (VM_Version::supports_avx512vl() == false) {
+    switch (vector_len) {
+    case AVX_128bit:
+    case AVX_256bit:
+      legacy_mode = true;
+      break;
+    }
+  }
+
+  if ((UseAVX > 2) && (legacy_mode == false))
+  {
+    bool evex_r = (dst_enc >= 16);
+    bool evex_v = (nds_enc >= 16);
+    // can use vex_x as bank extender on rm encoding
+    vex_x = (src_enc >= 16);
+    evex_prefix(vex_r, vex_b, vex_x, vex_w, evex_r, evex_v, nds_enc, pre, opc, false, false, vector_len, no_mask_reg);
+  } else {
+    vex_prefix(vex_r, vex_b, vex_x, vex_w, nds_enc, pre, opc, vector_len);
+  }
+
+  // return modrm byte components for operands
   return (((dst_enc & 7) << 3) | (src_enc & 7));
 }
 
 
-void Assembler::simd_prefix(XMMRegister xreg, XMMRegister nds, Address adr, VexSimdPrefix pre, VexOpcode opc, bool rex_w, bool vector256) {
+void Assembler::simd_prefix(XMMRegister xreg, XMMRegister nds, Address adr, VexSimdPrefix pre,
+                            bool no_mask_reg, VexOpcode opc, bool rex_w, int vector_len, bool legacy_mode) {
   if (UseAVX > 0) {
     int xreg_enc = xreg->encoding();
     int  nds_enc = nds->is_valid() ? nds->encoding() : 0;
-    vex_prefix(adr, nds_enc, xreg_enc, pre, opc, rex_w, vector256);
+    vex_prefix(adr, nds_enc, xreg_enc, pre, opc, rex_w, vector_len, legacy_mode, no_mask_reg);
   } else {
     assert((nds == xreg) || (nds == xnoreg), "wrong sse encoding");
     rex_prefix(adr, xreg, pre, opc, rex_w);
   }
 }
 
-int Assembler::simd_prefix_and_encode(XMMRegister dst, XMMRegister nds, XMMRegister src, VexSimdPrefix pre, VexOpcode opc, bool rex_w, bool vector256) {
+int Assembler::simd_prefix_and_encode(XMMRegister dst, XMMRegister nds, XMMRegister src, VexSimdPrefix pre,
+                                      bool no_mask_reg, VexOpcode opc, bool rex_w, int vector_len, bool legacy_mode) {
   int dst_enc = dst->encoding();
   int src_enc = src->encoding();
   if (UseAVX > 0) {
     int nds_enc = nds->is_valid() ? nds->encoding() : 0;
-    return vex_prefix_and_encode(dst_enc, nds_enc, src_enc, pre, opc, rex_w, vector256);
+    return vex_prefix_and_encode(dst_enc, nds_enc, src_enc, pre, opc, rex_w, vector_len, legacy_mode, no_mask_reg);
   } else {
     assert((nds == dst) || (nds == src) || (nds == xnoreg), "wrong sse encoding");
     return rex_prefix_and_encode(dst_enc, src_enc, pre, opc, rex_w);
   }
 }
 
-void Assembler::emit_simd_arith(int opcode, XMMRegister dst, Address src, VexSimdPrefix pre) {
-  InstructionMark im(this);
-  simd_prefix(dst, dst, src, pre);
+int Assembler::kreg_prefix_and_encode(KRegister dst, KRegister nds, KRegister src, VexSimdPrefix pre,
+                                      bool no_mask_reg, VexOpcode opc, bool rex_w, int vector_len) {
+  int dst_enc = dst->encoding();
+  int src_enc = src->encoding();
+  int nds_enc = nds->is_valid() ? nds->encoding() : 0;
+  return vex_prefix_and_encode(dst_enc, nds_enc, src_enc, pre, opc, rex_w, vector_len, true, no_mask_reg);
+}
+
+int Assembler::kreg_prefix_and_encode(KRegister dst, KRegister nds, Register src, VexSimdPrefix pre,
+                                      bool no_mask_reg, VexOpcode opc, bool rex_w, int vector_len) {
+  int dst_enc = dst->encoding();
+  int src_enc = src->encoding();
+  int nds_enc = nds->is_valid() ? nds->encoding() : 0;
+  return vex_prefix_and_encode(dst_enc, nds_enc, src_enc, pre, opc, rex_w, vector_len, true, no_mask_reg);
+}
+
+void Assembler::emit_simd_arith(int opcode, XMMRegister dst, Address src, VexSimdPrefix pre, bool no_mask_reg, bool legacy_mode) {
+  InstructionMark im(this);
+  simd_prefix(dst, dst, src, pre, no_mask_reg, VEX_OPCODE_0F, false, AVX_128bit, legacy_mode);
   emit_int8(opcode);
   emit_operand(dst, src);
 }
 
-void Assembler::emit_simd_arith(int opcode, XMMRegister dst, XMMRegister src, VexSimdPrefix pre) {
-  int encode = simd_prefix_and_encode(dst, dst, src, pre);
+void Assembler::emit_simd_arith_q(int opcode, XMMRegister dst, Address src, VexSimdPrefix pre, bool no_mask_reg) {
+  InstructionMark im(this);
+  simd_prefix_q(dst, dst, src, pre, no_mask_reg);
+  emit_int8(opcode);
+  emit_operand(dst, src);
+}
+
+void Assembler::emit_simd_arith(int opcode, XMMRegister dst, XMMRegister src, VexSimdPrefix pre, bool no_mask_reg, bool legacy_mode) {
+  int encode = simd_prefix_and_encode(dst, dst, src, pre, no_mask_reg, VEX_OPCODE_0F, false, AVX_128bit, legacy_mode);
+  emit_int8(opcode);
+  emit_int8((unsigned char)(0xC0 | encode));
+}
+
+void Assembler::emit_simd_arith_q(int opcode, XMMRegister dst, XMMRegister src, VexSimdPrefix pre, bool no_mask_reg) {
+  int encode = simd_prefix_and_encode(dst, dst, src, pre, no_mask_reg, VEX_OPCODE_0F, true, AVX_128bit);
   emit_int8(opcode);
   emit_int8((unsigned char)(0xC0 | encode));
 }
 
 // Versions with no second source register (non-destructive source).
-void Assembler::emit_simd_arith_nonds(int opcode, XMMRegister dst, Address src, VexSimdPrefix pre) {
-  InstructionMark im(this);
-  simd_prefix(dst, xnoreg, src, pre);
+void Assembler::emit_simd_arith_nonds(int opcode, XMMRegister dst, Address src, VexSimdPrefix pre, bool opNoRegMask) {
+  InstructionMark im(this);
+  simd_prefix(dst, xnoreg, src, pre, opNoRegMask);
   emit_int8(opcode);
   emit_operand(dst, src);
 }
 
-void Assembler::emit_simd_arith_nonds(int opcode, XMMRegister dst, XMMRegister src, VexSimdPrefix pre) {
-  int encode = simd_prefix_and_encode(dst, xnoreg, src, pre);
+void Assembler::emit_simd_arith_nonds_q(int opcode, XMMRegister dst, Address src, VexSimdPrefix pre, bool opNoRegMask) {
+  InstructionMark im(this);
+  simd_prefix_q(dst, xnoreg, src, pre, opNoRegMask);
+  emit_int8(opcode);
+  emit_operand(dst, src);
+}
+
+void Assembler::emit_simd_arith_nonds(int opcode, XMMRegister dst, XMMRegister src, VexSimdPrefix pre, bool no_mask_reg, bool legacy_mode) {
+  int encode = simd_prefix_and_encode(dst, xnoreg, src, pre, no_mask_reg, VEX_OPCODE_0F, legacy_mode, AVX_128bit);
+  emit_int8(opcode);
+  emit_int8((unsigned char)(0xC0 | encode));
+}
+
+void Assembler::emit_simd_arith_nonds_q(int opcode, XMMRegister dst, XMMRegister src, VexSimdPrefix pre, bool no_mask_reg) {
+  int encode = simd_prefix_and_encode(dst, xnoreg, src, pre, no_mask_reg, VEX_OPCODE_0F, true, AVX_128bit);
   emit_int8(opcode);
   emit_int8((unsigned char)(0xC0 | encode));
 }
 
 // 3-operands AVX instructions
-void Assembler::emit_vex_arith(int opcode, XMMRegister dst, XMMRegister nds,
-                               Address src, VexSimdPrefix pre, bool vector256) {
-  InstructionMark im(this);
-  vex_prefix(dst, nds, src, pre, vector256);
+void Assembler::emit_vex_arith(int opcode, XMMRegister dst, XMMRegister nds, Address src,
+                               VexSimdPrefix pre, int vector_len, bool no_mask_reg, bool legacy_mode) {
+  InstructionMark im(this);
+  vex_prefix(dst, nds, src, pre, vector_len, no_mask_reg, legacy_mode);
+  emit_int8(opcode);
+  emit_operand(dst, src);
+}
+
+void Assembler::emit_vex_arith_q(int opcode, XMMRegister dst, XMMRegister nds,
+                                 Address src, VexSimdPrefix pre, int vector_len, bool no_mask_reg) {
+  InstructionMark im(this);
+  vex_prefix_q(dst, nds, src, pre, vector_len, no_mask_reg);
   emit_int8(opcode);
   emit_operand(dst, src);
 }
 
-void Assembler::emit_vex_arith(int opcode, XMMRegister dst, XMMRegister nds,
-                               XMMRegister src, VexSimdPrefix pre, bool vector256) {
-  int encode = vex_prefix_and_encode(dst, nds, src, pre, vector256);
+void Assembler::emit_vex_arith(int opcode, XMMRegister dst, XMMRegister nds, XMMRegister src,
+                               VexSimdPrefix pre, int vector_len, bool no_mask_reg, bool legacy_mode) {
+  int encode = vex_prefix_and_encode(dst, nds, src, pre, vector_len, VEX_OPCODE_0F, false, no_mask_reg);
+  emit_int8(opcode);
+  emit_int8((unsigned char)(0xC0 | encode));
+}
+
+void Assembler::emit_vex_arith_q(int opcode, XMMRegister dst, XMMRegister nds, XMMRegister src,
+                                 VexSimdPrefix pre, int vector_len, bool no_mask_reg) {
+  int src_enc = src->encoding();
+  int dst_enc = dst->encoding();
+  int nds_enc = nds->is_valid() ? nds->encoding() : 0;
+  int encode = vex_prefix_and_encode(dst_enc, nds_enc, src_enc, pre, VEX_OPCODE_0F, true, vector_len, false, no_mask_reg);
   emit_int8(opcode);
   emit_int8((unsigned char)(0xC0 | encode));
 }
@@ -5040,6 +6271,10 @@
 }
 
 void Assembler::andnq(Register dst, Register src1, Address src2) {
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_64bit;
+  }
   InstructionMark im(this);
   assert(VM_Version::supports_bmi1(), "bit manipulation instructions not supported");
   vex_prefix_0F38_q(dst, src1, src2);
@@ -5181,44 +6416,52 @@
 
 void Assembler::cvtsi2sdq(XMMRegister dst, Register src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  int encode = simd_prefix_and_encode_q(dst, dst, src, VEX_SIMD_F2);
+  int encode = simd_prefix_and_encode_q(dst, dst, src, VEX_SIMD_F2, true);
   emit_int8(0x2A);
   emit_int8((unsigned char)(0xC0 | encode));
 }
 
 void Assembler::cvtsi2sdq(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  InstructionMark im(this);
-  simd_prefix_q(dst, dst, src, VEX_SIMD_F2);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+  }
+  InstructionMark im(this);
+  simd_prefix_q(dst, dst, src, VEX_SIMD_F2, true);
   emit_int8(0x2A);
   emit_operand(dst, src);
 }
 
 void Assembler::cvtsi2ssq(XMMRegister dst, Register src) {
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
-  int encode = simd_prefix_and_encode_q(dst, dst, src, VEX_SIMD_F3);
+  int encode = simd_prefix_and_encode_q(dst, dst, src, VEX_SIMD_F3, true);
   emit_int8(0x2A);
   emit_int8((unsigned char)(0xC0 | encode));
 }
 
 void Assembler::cvtsi2ssq(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
-  InstructionMark im(this);
-  simd_prefix_q(dst, dst, src, VEX_SIMD_F3);
+  if (VM_Version::supports_evex()) {
+    tuple_type = EVEX_T1S;
+    input_size_in_bits = EVEX_32bit;
+  }
+  InstructionMark im(this);
+  simd_prefix_q(dst, dst, src, VEX_SIMD_F3, true);
   emit_int8(0x2A);
   emit_operand(dst, src);
 }
 
 void Assembler::cvttsd2siq(Register dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  int encode = simd_prefix_and_encode_q(dst, src, VEX_SIMD_F2);
+  int encode = simd_prefix_and_encode_q(dst, src, VEX_SIMD_F2, VEX_OPCODE_0F, true);
   emit_int8(0x2C);
   emit_int8((unsigned char)(0xC0 | encode));
 }
 
 void Assembler::cvttss2siq(Register dst, XMMRegister src) {
   NOT_LP64(assert(VM_Version::supports_sse(), ""));
-  int encode = simd_prefix_and_encode_q(dst, src, VEX_SIMD_F3);
+  int encode = simd_prefix_and_encode_q(dst, src, VEX_SIMD_F3, VEX_OPCODE_0F, true);
   emit_int8(0x2C);
   emit_int8((unsigned char)(0xC0 | encode));
 }
@@ -5387,7 +6630,7 @@
 void Assembler::movdq(XMMRegister dst, Register src) {
   // table D-1 says MMX/SSE2
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
-  int encode = simd_prefix_and_encode_q(dst, src, VEX_SIMD_66);
+  int encode = simd_prefix_and_encode_q(dst, src, VEX_SIMD_66, true);
   emit_int8(0x6E);
   emit_int8((unsigned char)(0xC0 | encode));
 }
@@ -5396,7 +6639,7 @@
   // table D-1 says MMX/SSE2
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
   // swap src/dst to get correct prefix
-  int encode = simd_prefix_and_encode_q(src, dst, VEX_SIMD_66);
+  int encode = simd_prefix_and_encode_q(src, dst, VEX_SIMD_66, true);
   emit_int8(0x7E);
   emit_int8((unsigned char)(0xC0 | encode));
 }
@@ -5529,7 +6772,8 @@
 
 void Assembler::mulxq(Register dst1, Register dst2, Register src) {
   assert(VM_Version::supports_bmi2(), "bit manipulation instructions not supported");
-  int encode = vex_prefix_and_encode(dst1->encoding(), dst2->encoding(), src->encoding(), VEX_SIMD_F2, VEX_OPCODE_0F_38, true, false);
+  int encode = vex_prefix_and_encode(dst1->encoding(), dst2->encoding(), src->encoding(),
+                                     VEX_SIMD_F2, VEX_OPCODE_0F_38, true, AVX_128bit, true, false);
   emit_int8((unsigned char)0xF6);
   emit_int8((unsigned char)(0xC0 | encode));
 }
@@ -5678,7 +6922,8 @@
 
 void Assembler::rorxq(Register dst, Register src, int imm8) {
   assert(VM_Version::supports_bmi2(), "bit manipulation instructions not supported");
-  int encode = vex_prefix_and_encode(dst->encoding(), 0, src->encoding(), VEX_SIMD_F2, VEX_OPCODE_0F_3A, true, false);
+  int encode = vex_prefix_and_encode(dst->encoding(), 0, src->encoding(), VEX_SIMD_F2,
+                                     VEX_OPCODE_0F_3A, true, AVX_128bit, true, false);
   emit_int8((unsigned char)0xF0);
   emit_int8((unsigned char)(0xC0 | encode));
   emit_int8(imm8);
--- a/hotspot/src/cpu/x86/vm/assembler_x86.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/assembler_x86.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -438,7 +438,7 @@
 
 };
 
-const int FPUStateSizeInWords = NOT_LP64(27) LP64_ONLY( 512 / wordSize);
+const int FPUStateSizeInWords = NOT_LP64(27) LP64_ONLY( 512*2 / wordSize);
 
 // The Intel x86/Amd64 Assembler: Pure assembler doing NO optimizations on the instruction
 // level (e.g. mov rax, 0 is not translated into xor rax, rax!); i.e., what you write
@@ -503,7 +503,8 @@
     REX_WRXB   = 0x4F,
 
     VEX_3bytes = 0xC4,
-    VEX_2bytes = 0xC5
+    VEX_2bytes = 0xC5,
+    EVEX_4bytes = 0x62
   };
 
   enum VexPrefix {
@@ -513,6 +514,14 @@
     VEX_W = 0x80
   };
 
+  enum ExexPrefix {
+    EVEX_F  = 0x04,
+    EVEX_V  = 0x08,
+    EVEX_Rb = 0x10,
+    EVEX_X  = 0x40,
+    EVEX_Z  = 0x80
+  };
+
   enum VexSimdPrefix {
     VEX_SIMD_NONE = 0x0,
     VEX_SIMD_66   = 0x1,
@@ -527,6 +536,37 @@
     VEX_OPCODE_0F_3A = 0x3
   };
 
+  enum AvxVectorLen {
+    AVX_128bit = 0x0,
+    AVX_256bit = 0x1,
+    AVX_512bit = 0x2,
+    AVX_NoVec  = 0x4
+  };
+
+  enum EvexTupleType {
+    EVEX_FV   = 0,
+    EVEX_HV   = 4,
+    EVEX_FVM  = 6,
+    EVEX_T1S  = 7,
+    EVEX_T1F  = 11,
+    EVEX_T2   = 13,
+    EVEX_T4   = 15,
+    EVEX_T8   = 17,
+    EVEX_HVM  = 18,
+    EVEX_QVM  = 19,
+    EVEX_OVM  = 20,
+    EVEX_M128 = 21,
+    EVEX_DUP  = 22,
+    EVEX_ETUP = 23
+  };
+
+  enum EvexInputSizeInBits {
+    EVEX_8bit  = 0,
+    EVEX_16bit = 1,
+    EVEX_32bit = 2,
+    EVEX_64bit = 3
+  };
+
   enum WhichOperand {
     // input to locate_operand, and format code for relocations
     imm_operand  = 0,            // embedded 32-bit|64-bit immediate operand
@@ -554,6 +594,11 @@
 
 private:
 
+  int evex_encoding;
+  int input_size_in_bits;
+  int avx_vector_len;
+  int tuple_type;
+  bool is_evex_instruction;
 
   // 64bit prefixes
   int prefix_and_encode(int reg_enc, bool byteinst = false);
@@ -580,108 +625,143 @@
 
   void vex_prefix(bool vex_r, bool vex_b, bool vex_x, bool vex_w,
                   int nds_enc, VexSimdPrefix pre, VexOpcode opc,
-                  bool vector256);
+                  int vector_len);
+
+  void evex_prefix(bool vex_r, bool vex_b, bool vex_x, bool vex_w, bool evex_r, bool evex_v,
+                   int nds_enc, VexSimdPrefix pre, VexOpcode opc,
+                   bool is_extended_context, bool is_merge_context,
+                   int vector_len, bool no_mask_reg );
 
   void vex_prefix(Address adr, int nds_enc, int xreg_enc,
                   VexSimdPrefix pre, VexOpcode opc,
-                  bool vex_w, bool vector256);
+                  bool vex_w, int vector_len,
+                  bool legacy_mode = false, bool no_mask_reg = false);
 
   void vex_prefix(XMMRegister dst, XMMRegister nds, Address src,
-                  VexSimdPrefix pre, bool vector256 = false) {
+                  VexSimdPrefix pre, int vector_len = AVX_128bit,
+                  bool no_mask_reg = false, bool legacy_mode = false) {
     int dst_enc = dst->encoding();
     int nds_enc = nds->is_valid() ? nds->encoding() : 0;
-    vex_prefix(src, nds_enc, dst_enc, pre, VEX_OPCODE_0F, false, vector256);
+    vex_prefix(src, nds_enc, dst_enc, pre, VEX_OPCODE_0F, false, vector_len, legacy_mode, no_mask_reg);
   }
 
-  void vex_prefix_0F38(Register dst, Register nds, Address src) {
-    bool vex_w = false;
-    bool vector256 = false;
-    vex_prefix(src, nds->encoding(), dst->encoding(),
-               VEX_SIMD_NONE, VEX_OPCODE_0F_38, vex_w, vector256);
+  void vex_prefix_q(XMMRegister dst, XMMRegister nds, Address src,
+                    VexSimdPrefix pre, int vector_len = AVX_128bit,
+                    bool no_mask_reg = false) {
+    int dst_enc = dst->encoding();
+    int nds_enc = nds->is_valid() ? nds->encoding() : 0;
+    vex_prefix(src, nds_enc, dst_enc, pre, VEX_OPCODE_0F, true, vector_len, false, no_mask_reg);
   }
 
-  void vex_prefix_0F38_q(Register dst, Register nds, Address src) {
+  void vex_prefix_0F38(Register dst, Register nds, Address src, bool no_mask_reg = false) {
+    bool vex_w = false;
+    int vector_len = AVX_128bit;
+    vex_prefix(src, nds->encoding(), dst->encoding(),
+               VEX_SIMD_NONE, VEX_OPCODE_0F_38, vex_w,
+               vector_len, no_mask_reg);
+  }
+
+  void vex_prefix_0F38_q(Register dst, Register nds, Address src, bool no_mask_reg = false) {
     bool vex_w = true;
-    bool vector256 = false;
+    int vector_len = AVX_128bit;
     vex_prefix(src, nds->encoding(), dst->encoding(),
-               VEX_SIMD_NONE, VEX_OPCODE_0F_38, vex_w, vector256);
+               VEX_SIMD_NONE, VEX_OPCODE_0F_38, vex_w,
+               vector_len, no_mask_reg);
   }
   int  vex_prefix_and_encode(int dst_enc, int nds_enc, int src_enc,
                              VexSimdPrefix pre, VexOpcode opc,
-                             bool vex_w, bool vector256);
+                             bool vex_w, int vector_len,
+                             bool legacy_mode, bool no_mask_reg);
 
-  int  vex_prefix_0F38_and_encode(Register dst, Register nds, Register src) {
+  int  vex_prefix_0F38_and_encode(Register dst, Register nds, Register src, bool no_mask_reg = false) {
     bool vex_w = false;
-    bool vector256 = false;
+    int vector_len = AVX_128bit;
     return vex_prefix_and_encode(dst->encoding(), nds->encoding(), src->encoding(),
-                                 VEX_SIMD_NONE, VEX_OPCODE_0F_38, vex_w, vector256);
+                                 VEX_SIMD_NONE, VEX_OPCODE_0F_38, vex_w, vector_len,
+                                 false, no_mask_reg);
   }
-  int  vex_prefix_0F38_and_encode_q(Register dst, Register nds, Register src) {
+  int  vex_prefix_0F38_and_encode_q(Register dst, Register nds, Register src, bool no_mask_reg = false) {
     bool vex_w = true;
-    bool vector256 = false;
+    int vector_len = AVX_128bit;
     return vex_prefix_and_encode(dst->encoding(), nds->encoding(), src->encoding(),
-                                 VEX_SIMD_NONE, VEX_OPCODE_0F_38, vex_w, vector256);
+                                 VEX_SIMD_NONE, VEX_OPCODE_0F_38, vex_w, vector_len,
+                                 false, no_mask_reg);
   }
   int  vex_prefix_and_encode(XMMRegister dst, XMMRegister nds, XMMRegister src,
-                             VexSimdPrefix pre, bool vector256 = false,
-                             VexOpcode opc = VEX_OPCODE_0F) {
+                             VexSimdPrefix pre, int vector_len = AVX_128bit,
+                             VexOpcode opc = VEX_OPCODE_0F, bool legacy_mode = false,
+                             bool no_mask_reg = false) {
     int src_enc = src->encoding();
     int dst_enc = dst->encoding();
     int nds_enc = nds->is_valid() ? nds->encoding() : 0;
-    return vex_prefix_and_encode(dst_enc, nds_enc, src_enc, pre, opc, false, vector256);
+    return vex_prefix_and_encode(dst_enc, nds_enc, src_enc, pre, opc, false, vector_len, legacy_mode, no_mask_reg);
   }
 
   void simd_prefix(XMMRegister xreg, XMMRegister nds, Address adr,
-                   VexSimdPrefix pre, VexOpcode opc = VEX_OPCODE_0F,
-                   bool rex_w = false, bool vector256 = false);
+                   VexSimdPrefix pre, bool no_mask_reg, VexOpcode opc = VEX_OPCODE_0F,
+                   bool rex_w = false, int vector_len = AVX_128bit, bool legacy_mode = false);
 
-  void simd_prefix(XMMRegister dst, Address src,
-                   VexSimdPrefix pre, VexOpcode opc = VEX_OPCODE_0F) {
-    simd_prefix(dst, xnoreg, src, pre, opc);
+  void simd_prefix(XMMRegister dst, Address src, VexSimdPrefix pre,
+                   bool no_mask_reg, VexOpcode opc = VEX_OPCODE_0F) {
+    simd_prefix(dst, xnoreg, src, pre, no_mask_reg, opc);
   }
 
-  void simd_prefix(Address dst, XMMRegister src, VexSimdPrefix pre) {
-    simd_prefix(src, dst, pre);
+  void simd_prefix(Address dst, XMMRegister src, VexSimdPrefix pre, bool no_mask_reg) {
+    simd_prefix(src, dst, pre, no_mask_reg);
   }
   void simd_prefix_q(XMMRegister dst, XMMRegister nds, Address src,
-                     VexSimdPrefix pre) {
+                     VexSimdPrefix pre, bool no_mask_reg = false) {
     bool rex_w = true;
-    simd_prefix(dst, nds, src, pre, VEX_OPCODE_0F, rex_w);
+    simd_prefix(dst, nds, src, pre, no_mask_reg, VEX_OPCODE_0F, rex_w);
   }
 
   int simd_prefix_and_encode(XMMRegister dst, XMMRegister nds, XMMRegister src,
-                             VexSimdPrefix pre, VexOpcode opc = VEX_OPCODE_0F,
-                             bool rex_w = false, bool vector256 = false);
+                             VexSimdPrefix pre, bool no_mask_reg,
+                             VexOpcode opc = VEX_OPCODE_0F,
+                             bool rex_w = false, int vector_len = AVX_128bit,
+                             bool legacy_mode = false);
+
+  int kreg_prefix_and_encode(KRegister dst, KRegister nds, KRegister src,
+                             VexSimdPrefix pre, bool no_mask_reg,
+                             VexOpcode opc = VEX_OPCODE_0F,
+                             bool rex_w = false, int vector_len = AVX_128bit);
+
+  int kreg_prefix_and_encode(KRegister dst, KRegister nds, Register src,
+                             VexSimdPrefix pre, bool no_mask_reg,
+                             VexOpcode opc = VEX_OPCODE_0F,
+                             bool rex_w = false, int vector_len = AVX_128bit);
 
   // Move/convert 32-bit integer value.
   int simd_prefix_and_encode(XMMRegister dst, XMMRegister nds, Register src,
-                             VexSimdPrefix pre) {
+                             VexSimdPrefix pre, bool no_mask_reg) {
     // It is OK to cast from Register to XMMRegister to pass argument here
     // since only encoding is used in simd_prefix_and_encode() and number of
     // Gen and Xmm registers are the same.
-    return simd_prefix_and_encode(dst, nds, as_XMMRegister(src->encoding()), pre);
+    return simd_prefix_and_encode(dst, nds, as_XMMRegister(src->encoding()), pre, no_mask_reg, VEX_OPCODE_0F);
   }
-  int simd_prefix_and_encode(XMMRegister dst, Register src, VexSimdPrefix pre) {
-    return simd_prefix_and_encode(dst, xnoreg, src, pre);
+  int simd_prefix_and_encode(XMMRegister dst, Register src, VexSimdPrefix pre, bool no_mask_reg) {
+    return simd_prefix_and_encode(dst, xnoreg, src, pre, no_mask_reg);
   }
   int simd_prefix_and_encode(Register dst, XMMRegister src,
-                             VexSimdPrefix pre, VexOpcode opc = VEX_OPCODE_0F) {
-    return simd_prefix_and_encode(as_XMMRegister(dst->encoding()), xnoreg, src, pre, opc);
+                             VexSimdPrefix pre, VexOpcode opc = VEX_OPCODE_0F,
+                             bool no_mask_reg = false) {
+    return simd_prefix_and_encode(as_XMMRegister(dst->encoding()), xnoreg, src, pre, no_mask_reg, opc);
   }
 
   // Move/convert 64-bit integer value.
   int simd_prefix_and_encode_q(XMMRegister dst, XMMRegister nds, Register src,
-                               VexSimdPrefix pre) {
+                               VexSimdPrefix pre, bool no_mask_reg = false) {
     bool rex_w = true;
-    return simd_prefix_and_encode(dst, nds, as_XMMRegister(src->encoding()), pre, VEX_OPCODE_0F, rex_w);
+    return simd_prefix_and_encode(dst, nds, as_XMMRegister(src->encoding()), pre, no_mask_reg, VEX_OPCODE_0F, rex_w);
   }
-  int simd_prefix_and_encode_q(XMMRegister dst, Register src, VexSimdPrefix pre) {
-    return simd_prefix_and_encode_q(dst, xnoreg, src, pre);
+  int simd_prefix_and_encode_q(XMMRegister dst, Register src, VexSimdPrefix pre, bool no_mask_reg) {
+    return simd_prefix_and_encode_q(dst, xnoreg, src, pre, no_mask_reg);
   }
   int simd_prefix_and_encode_q(Register dst, XMMRegister src,
-                             VexSimdPrefix pre, VexOpcode opc = VEX_OPCODE_0F) {
+                               VexSimdPrefix pre, VexOpcode opc = VEX_OPCODE_0F,
+                               bool no_mask_reg = false) {
     bool rex_w = true;
-    return simd_prefix_and_encode(as_XMMRegister(dst->encoding()), xnoreg, src, pre, opc, rex_w);
+    return simd_prefix_and_encode(as_XMMRegister(dst->encoding()), xnoreg, src, pre, no_mask_reg, opc, rex_w);
   }
 
   // Helper functions for groups of instructions
@@ -692,14 +772,28 @@
   void emit_arith_imm32(int op1, int op2, Register dst, int32_t imm32);
   void emit_arith(int op1, int op2, Register dst, Register src);
 
-  void emit_simd_arith(int opcode, XMMRegister dst, Address src, VexSimdPrefix pre);
-  void emit_simd_arith(int opcode, XMMRegister dst, XMMRegister src, VexSimdPrefix pre);
-  void emit_simd_arith_nonds(int opcode, XMMRegister dst, Address src, VexSimdPrefix pre);
-  void emit_simd_arith_nonds(int opcode, XMMRegister dst, XMMRegister src, VexSimdPrefix pre);
+  void emit_simd_arith(int opcode, XMMRegister dst, Address src, VexSimdPrefix pre, bool no_mask_reg = false, bool legacy_mode = false);
+  void emit_simd_arith_q(int opcode, XMMRegister dst, Address src, VexSimdPrefix pre, bool no_mask_reg = false);
+  void emit_simd_arith(int opcode, XMMRegister dst, XMMRegister src, VexSimdPrefix pre, bool no_mask_reg = false, bool legacy_mode = false);
+  void emit_simd_arith_q(int opcode, XMMRegister dst, XMMRegister src, VexSimdPrefix pre, bool no_mask_reg = false);
+  void emit_simd_arith_nonds(int opcode, XMMRegister dst, Address src, VexSimdPrefix pre, bool no_mask_reg = false);
+  void emit_simd_arith_nonds_q(int opcode, XMMRegister dst, Address src, VexSimdPrefix pre, bool no_mask_reg = false);
+  void emit_simd_arith_nonds(int opcode, XMMRegister dst, XMMRegister src, VexSimdPrefix pre, bool no_mask_reg = false, bool legacy_mode = false);
+  void emit_simd_arith_nonds_q(int opcode, XMMRegister dst, XMMRegister src, VexSimdPrefix pre, bool no_mask_reg = false);
   void emit_vex_arith(int opcode, XMMRegister dst, XMMRegister nds,
-                      Address src, VexSimdPrefix pre, bool vector256);
+                      Address src, VexSimdPrefix pre, int vector_len,
+                      bool no_mask_reg = false, bool legacy_mode = false);
+  void emit_vex_arith_q(int opcode, XMMRegister dst, XMMRegister nds,
+                        Address src, VexSimdPrefix pre, int vector_len,
+                        bool no_mask_reg = false);
   void emit_vex_arith(int opcode, XMMRegister dst, XMMRegister nds,
-                      XMMRegister src, VexSimdPrefix pre, bool vector256);
+                      XMMRegister src, VexSimdPrefix pre, int vector_len,
+                      bool no_mask_reg = false, bool legacy_mode = false);
+  void emit_vex_arith_q(int opcode, XMMRegister dst, XMMRegister nds,
+                        XMMRegister src, VexSimdPrefix pre, int vector_len,
+                        bool no_mask_reg = false);
+
+  bool emit_compressed_disp_byte(int &disp);
 
   void emit_operand(Register reg,
                     Register base, Register index, Address::ScaleFactor scale,
@@ -825,7 +919,9 @@
   public:
 
   // Creation
-  Assembler(CodeBuffer* code) : AbstractAssembler(code) {}
+  Assembler(CodeBuffer* code) : AbstractAssembler(code) {
+    init_attributes();
+  }
 
   // Decoding
   static address locate_operand(address inst, WhichOperand which);
@@ -833,11 +929,21 @@
 
   // Utilities
   static bool is_polling_page_far() NOT_LP64({ return false;});
+  static bool query_compressed_disp_byte(int disp, bool is_evex_inst, int vector_len,
+                                         int cur_tuple_type, int in_size_in_bits, int cur_encoding);
 
   // Generic instructions
   // Does 32bit or 64bit as needed for the platform. In some sense these
   // belong in macro assembler but there is no need for both varieties to exist
 
+  void init_attributes(void) {
+    evex_encoding = 0;
+    input_size_in_bits = 0;
+    avx_vector_len = AVX_NoVec;
+    tuple_type = EVEX_ETUP;
+    is_evex_instruction = false;
+  }
+
   void lea(Register dst, Address src);
 
   void mov(Register dst, Register src);
@@ -1338,6 +1444,12 @@
   void movb(Address dst, int imm8);
   void movb(Register dst, Address src);
 
+  void kmovq(KRegister dst, KRegister src);
+  void kmovql(KRegister dst, Register src);
+  void kmovdl(KRegister dst, Register src);
+  void kmovq(Address dst, KRegister src);
+  void kmovq(KRegister dst, Address src);
+
   void movdl(XMMRegister dst, Register src);
   void movdl(Register dst, XMMRegister src);
   void movdl(XMMRegister dst, Address src);
@@ -1361,6 +1473,11 @@
   void vmovdqu(XMMRegister dst, Address src);
   void vmovdqu(XMMRegister dst, XMMRegister src);
 
+   // Move Unaligned 512bit Vector
+  void evmovdqu(Address dst, XMMRegister src, int vector_len);
+  void evmovdqu(XMMRegister dst, Address src, int vector_len);
+  void evmovdqu(XMMRegister dst, XMMRegister src, int vector_len);
+
   // Move lower 64bit to high 64bit in 128bit register
   void movlhps(XMMRegister dst, XMMRegister src);
 
@@ -1486,10 +1603,10 @@
   // Pack with unsigned saturation
   void packuswb(XMMRegister dst, XMMRegister src);
   void packuswb(XMMRegister dst, Address src);
-  void vpackuswb(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
+  void vpackuswb(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
 
   // Pemutation of 64bit words
-  void vpermq(XMMRegister dst, XMMRegister src, int imm8, bool vector256);
+  void vpermq(XMMRegister dst, XMMRegister src, int imm8, int vector_len);
 
   void pause();
 
@@ -1734,54 +1851,54 @@
   // Add Packed Floating-Point Values
   void addpd(XMMRegister dst, XMMRegister src);
   void addps(XMMRegister dst, XMMRegister src);
-  void vaddpd(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vaddps(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vaddpd(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
-  void vaddps(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
+  void vaddpd(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vaddps(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vaddpd(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
+  void vaddps(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
 
   // Subtract Packed Floating-Point Values
   void subpd(XMMRegister dst, XMMRegister src);
   void subps(XMMRegister dst, XMMRegister src);
-  void vsubpd(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vsubps(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vsubpd(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
-  void vsubps(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
+  void vsubpd(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vsubps(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vsubpd(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
+  void vsubps(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
 
   // Multiply Packed Floating-Point Values
   void mulpd(XMMRegister dst, XMMRegister src);
   void mulps(XMMRegister dst, XMMRegister src);
-  void vmulpd(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vmulps(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vmulpd(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
-  void vmulps(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
+  void vmulpd(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vmulps(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vmulpd(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
+  void vmulps(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
 
   // Divide Packed Floating-Point Values
   void divpd(XMMRegister dst, XMMRegister src);
   void divps(XMMRegister dst, XMMRegister src);
-  void vdivpd(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vdivps(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vdivpd(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
-  void vdivps(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
+  void vdivpd(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vdivps(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vdivpd(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
+  void vdivps(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
 
   // Bitwise Logical AND of Packed Floating-Point Values
   void andpd(XMMRegister dst, XMMRegister src);
   void andps(XMMRegister dst, XMMRegister src);
-  void vandpd(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vandps(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vandpd(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
-  void vandps(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
+  void vandpd(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vandps(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vandpd(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
+  void vandps(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
 
   // Bitwise Logical XOR of Packed Floating-Point Values
   void xorpd(XMMRegister dst, XMMRegister src);
   void xorps(XMMRegister dst, XMMRegister src);
-  void vxorpd(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vxorps(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vxorpd(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
-  void vxorps(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
+  void vxorpd(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vxorps(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vxorpd(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
+  void vxorps(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
 
   // Add horizontal packed integers
-  void vphaddw(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vphaddd(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
+  void vphaddw(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vphaddd(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
   void phaddw(XMMRegister dst, XMMRegister src);
   void phaddd(XMMRegister dst, XMMRegister src);
 
@@ -1790,36 +1907,38 @@
   void paddw(XMMRegister dst, XMMRegister src);
   void paddd(XMMRegister dst, XMMRegister src);
   void paddq(XMMRegister dst, XMMRegister src);
-  void vpaddb(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vpaddw(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vpaddd(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vpaddq(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vpaddb(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
-  void vpaddw(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
-  void vpaddd(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
-  void vpaddq(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
+  void vpaddb(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vpaddw(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vpaddd(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vpaddq(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vpaddb(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
+  void vpaddw(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
+  void vpaddd(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
+  void vpaddq(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
 
   // Sub packed integers
   void psubb(XMMRegister dst, XMMRegister src);
   void psubw(XMMRegister dst, XMMRegister src);
   void psubd(XMMRegister dst, XMMRegister src);
   void psubq(XMMRegister dst, XMMRegister src);
-  void vpsubb(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vpsubw(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vpsubd(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vpsubq(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vpsubb(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
-  void vpsubw(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
-  void vpsubd(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
-  void vpsubq(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
+  void vpsubb(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vpsubw(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vpsubd(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vpsubq(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vpsubb(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
+  void vpsubw(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
+  void vpsubd(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
+  void vpsubq(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
 
   // Multiply packed integers (only shorts and ints)
   void pmullw(XMMRegister dst, XMMRegister src);
   void pmulld(XMMRegister dst, XMMRegister src);
-  void vpmullw(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vpmulld(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vpmullw(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
-  void vpmulld(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
+  void vpmullw(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vpmulld(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vpmullq(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vpmullw(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
+  void vpmulld(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
+  void vpmullq(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
 
   // Shift left packed integers
   void psllw(XMMRegister dst, int shift);
@@ -1828,12 +1947,12 @@
   void psllw(XMMRegister dst, XMMRegister shift);
   void pslld(XMMRegister dst, XMMRegister shift);
   void psllq(XMMRegister dst, XMMRegister shift);
-  void vpsllw(XMMRegister dst, XMMRegister src, int shift, bool vector256);
-  void vpslld(XMMRegister dst, XMMRegister src, int shift, bool vector256);
-  void vpsllq(XMMRegister dst, XMMRegister src, int shift, bool vector256);
-  void vpsllw(XMMRegister dst, XMMRegister src, XMMRegister shift, bool vector256);
-  void vpslld(XMMRegister dst, XMMRegister src, XMMRegister shift, bool vector256);
-  void vpsllq(XMMRegister dst, XMMRegister src, XMMRegister shift, bool vector256);
+  void vpsllw(XMMRegister dst, XMMRegister src, int shift, int vector_len);
+  void vpslld(XMMRegister dst, XMMRegister src, int shift, int vector_len);
+  void vpsllq(XMMRegister dst, XMMRegister src, int shift, int vector_len);
+  void vpsllw(XMMRegister dst, XMMRegister src, XMMRegister shift, int vector_len);
+  void vpslld(XMMRegister dst, XMMRegister src, XMMRegister shift, int vector_len);
+  void vpsllq(XMMRegister dst, XMMRegister src, XMMRegister shift, int vector_len);
 
   // Logical shift right packed integers
   void psrlw(XMMRegister dst, int shift);
@@ -1842,42 +1961,43 @@
   void psrlw(XMMRegister dst, XMMRegister shift);
   void psrld(XMMRegister dst, XMMRegister shift);
   void psrlq(XMMRegister dst, XMMRegister shift);
-  void vpsrlw(XMMRegister dst, XMMRegister src, int shift, bool vector256);
-  void vpsrld(XMMRegister dst, XMMRegister src, int shift, bool vector256);
-  void vpsrlq(XMMRegister dst, XMMRegister src, int shift, bool vector256);
-  void vpsrlw(XMMRegister dst, XMMRegister src, XMMRegister shift, bool vector256);
-  void vpsrld(XMMRegister dst, XMMRegister src, XMMRegister shift, bool vector256);
-  void vpsrlq(XMMRegister dst, XMMRegister src, XMMRegister shift, bool vector256);
+  void vpsrlw(XMMRegister dst, XMMRegister src, int shift, int vector_len);
+  void vpsrld(XMMRegister dst, XMMRegister src, int shift, int vector_len);
+  void vpsrlq(XMMRegister dst, XMMRegister src, int shift, int vector_len);
+  void vpsrlw(XMMRegister dst, XMMRegister src, XMMRegister shift, int vector_len);
+  void vpsrld(XMMRegister dst, XMMRegister src, XMMRegister shift, int vector_len);
+  void vpsrlq(XMMRegister dst, XMMRegister src, XMMRegister shift, int vector_len);
 
   // Arithmetic shift right packed integers (only shorts and ints, no instructions for longs)
   void psraw(XMMRegister dst, int shift);
   void psrad(XMMRegister dst, int shift);
   void psraw(XMMRegister dst, XMMRegister shift);
   void psrad(XMMRegister dst, XMMRegister shift);
-  void vpsraw(XMMRegister dst, XMMRegister src, int shift, bool vector256);
-  void vpsrad(XMMRegister dst, XMMRegister src, int shift, bool vector256);
-  void vpsraw(XMMRegister dst, XMMRegister src, XMMRegister shift, bool vector256);
-  void vpsrad(XMMRegister dst, XMMRegister src, XMMRegister shift, bool vector256);
+  void vpsraw(XMMRegister dst, XMMRegister src, int shift, int vector_len);
+  void vpsrad(XMMRegister dst, XMMRegister src, int shift, int vector_len);
+  void vpsraw(XMMRegister dst, XMMRegister src, XMMRegister shift, int vector_len);
+  void vpsrad(XMMRegister dst, XMMRegister src, XMMRegister shift, int vector_len);
 
   // And packed integers
   void pand(XMMRegister dst, XMMRegister src);
-  void vpand(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vpand(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
+  void vpand(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vpand(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
 
   // Or packed integers
   void por(XMMRegister dst, XMMRegister src);
-  void vpor(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vpor(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
+  void vpor(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vpor(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
 
   // Xor packed integers
   void pxor(XMMRegister dst, XMMRegister src);
-  void vpxor(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256);
-  void vpxor(XMMRegister dst, XMMRegister nds, Address src, bool vector256);
+  void vpxor(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len);
+  void vpxor(XMMRegister dst, XMMRegister nds, Address src, int vector_len);
 
   // Copy low 128bit into high 128bit of YMM registers.
   void vinsertf128h(XMMRegister dst, XMMRegister nds, XMMRegister src);
   void vinserti128h(XMMRegister dst, XMMRegister nds, XMMRegister src);
   void vextractf128h(XMMRegister dst, XMMRegister src);
+  void vextracti128h(XMMRegister dst, XMMRegister src);
 
   // Load/store high 128bit of YMM registers which does not destroy other half.
   void vinsertf128h(XMMRegister dst, Address src);
@@ -1885,9 +2005,25 @@
   void vextractf128h(Address dst, XMMRegister src);
   void vextracti128h(Address dst, XMMRegister src);
 
+  // Copy low 256bit into high 256bit of ZMM registers.
+  void vinserti64x4h(XMMRegister dst, XMMRegister nds, XMMRegister src);
+  void vinsertf64x4h(XMMRegister dst, XMMRegister nds, XMMRegister src);
+  void vextracti64x4h(XMMRegister dst, XMMRegister src);
+  void vextractf64x4h(XMMRegister dst, XMMRegister src);
+  void vextractf64x4h(Address dst, XMMRegister src);
+  void vinsertf64x4h(XMMRegister dst, Address src);
+
+  // Copy targeted 128bit segments of the ZMM registers
+  void vextracti64x2h(XMMRegister dst, XMMRegister src, int value);
+  void vextractf64x2h(XMMRegister dst, XMMRegister src, int value);
+  void vextractf32x4h(XMMRegister dst, XMMRegister src, int value);
+
   // duplicate 4-bytes integer data from src into 8 locations in dest
   void vpbroadcastd(XMMRegister dst, XMMRegister src);
 
+  // duplicate 4-bytes integer data from src into vector_len locations in dest
+  void evpbroadcastd(XMMRegister dst, XMMRegister src, int vector_len);
+
   // Carry-Less Multiplication Quadword
   void pclmulqdq(XMMRegister dst, XMMRegister src, int mask);
   void vpclmulqdq(XMMRegister dst, XMMRegister nds, XMMRegister src, int mask);
--- a/hotspot/src/cpu/x86/vm/c1_FrameMap_x86.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/c1_FrameMap_x86.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -233,13 +233,30 @@
   _xmm_regs[13]  = xmm13;
   _xmm_regs[14]  = xmm14;
   _xmm_regs[15]  = xmm15;
+  _xmm_regs[16]  = xmm16;
+  _xmm_regs[17]  = xmm17;
+  _xmm_regs[18]  = xmm18;
+  _xmm_regs[19]  = xmm19;
+  _xmm_regs[20]  = xmm20;
+  _xmm_regs[21]  = xmm21;
+  _xmm_regs[22]  = xmm22;
+  _xmm_regs[23]  = xmm23;
+  _xmm_regs[24]  = xmm24;
+  _xmm_regs[25]  = xmm25;
+  _xmm_regs[26]  = xmm26;
+  _xmm_regs[27]  = xmm27;
+  _xmm_regs[28]  = xmm28;
+  _xmm_regs[29]  = xmm29;
+  _xmm_regs[30]  = xmm30;
+  _xmm_regs[31]  = xmm31;
 #endif // _LP64
 
   for (int i = 0; i < 8; i++) {
     _caller_save_fpu_regs[i] = LIR_OprFact::single_fpu(i);
   }
 
-  for (int i = 0; i < nof_caller_save_xmm_regs ; i++) {
+  int num_caller_save_xmm_regs = get_num_caller_save_xmms();
+  for (int i = 0; i < num_caller_save_xmm_regs; i++) {
     _caller_save_xmm_regs[i] = LIR_OprFact::single_xmm(i);
   }
 
--- a/hotspot/src/cpu/x86/vm/c1_FrameMap_x86.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/c1_FrameMap_x86.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -152,6 +152,16 @@
     return range;
   }
 
+  static int get_num_caller_save_xmms(void) {
+    int num_caller_save_xmm_regs = nof_caller_save_xmm_regs;
+#ifdef _LP64
+    if (UseAVX < 3) {
+      num_caller_save_xmm_regs = num_caller_save_xmm_regs / 2;
+    }
+#endif
+    return num_caller_save_xmm_regs;
+  }
+
   static int nof_caller_save_cpu_regs() { return adjust_reg_range(pd_nof_caller_save_cpu_regs_frame_map); }
   static int last_cpu_reg()             { return adjust_reg_range(pd_last_cpu_reg);  }
   static int last_byte_reg()            { return adjust_reg_range(pd_last_byte_reg); }
--- a/hotspot/src/cpu/x86/vm/c1_LinearScan_x86.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/c1_LinearScan_x86.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -85,8 +85,9 @@
           tty->print_cr("killing XMMs for trig");
         }
 #endif
+        int num_caller_save_xmm_regs = FrameMap::get_num_caller_save_xmms();
         int op_id = op->id();
-        for (int xmm = 0; xmm < FrameMap::nof_caller_save_xmm_regs; xmm++) {
+        for (int xmm = 0; xmm < num_caller_save_xmm_regs; xmm++) {
           LIR_Opr opr = FrameMap::caller_save_xmm_reg_at(xmm);
           add_temp(reg_num(opr), op_id, noUse, T_ILLEGAL);
         }
@@ -100,6 +101,10 @@
 // Implementation of LinearScanWalker
 
 inline bool LinearScanWalker::pd_init_regs_for_alloc(Interval* cur) {
+  int last_xmm_reg = pd_last_xmm_reg;
+  if (UseAVX < 3) {
+    last_xmm_reg = pd_first_xmm_reg + (pd_nof_xmm_regs_frame_map / 2) - 1;
+  }
   if (allocator()->gen()->is_vreg_flag_set(cur->reg_num(), LIRGenerator::byte_reg)) {
     assert(cur->type() != T_FLOAT && cur->type() != T_DOUBLE, "cpu regs only");
     _first_reg = pd_first_byte_reg;
@@ -107,7 +112,7 @@
     return true;
   } else if ((UseSSE >= 1 && cur->type() == T_FLOAT) || (UseSSE >= 2 && cur->type() == T_DOUBLE)) {
     _first_reg = pd_first_xmm_reg;
-    _last_reg = pd_last_xmm_reg;
+    _last_reg = last_xmm_reg;
     return true;
   }
 
--- a/hotspot/src/cpu/x86/vm/c1_Runtime1_x86.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/c1_Runtime1_x86.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -323,7 +323,7 @@
   LP64_ONLY(num_rt_args = 0);
   LP64_ONLY(assert((reg_save_frame_size * VMRegImpl::stack_slot_size) % 16 == 0, "must be 16 byte aligned");)
   int frame_size_in_slots = reg_save_frame_size + num_rt_args; // args + thread
-  sasm->set_frame_size(frame_size_in_slots / VMRegImpl::slots_per_word );
+  sasm->set_frame_size(frame_size_in_slots / VMRegImpl::slots_per_word);
 
   // record saved value locations in an OopMap
   // locations are offsets from sp after runtime call; num_rt_args is number of arguments in call, including thread
@@ -362,6 +362,13 @@
   map->set_callee_saved(VMRegImpl::stack2reg(r15H_off + num_rt_args), r15->as_VMReg()->next());
 #endif // _LP64
 
+  int xmm_bypass_limit = FrameMap::nof_xmm_regs;
+#ifdef _LP64
+  if (UseAVX < 3) {
+    xmm_bypass_limit = xmm_bypass_limit / 2;
+  }
+#endif
+
   if (save_fpu_registers) {
     if (UseSSE < 2) {
       int fpu_off = float_regs_as_doubles_off;
@@ -380,11 +387,13 @@
     if (UseSSE >= 2) {
       int xmm_off = xmm_regs_as_doubles_off;
       for (int n = 0; n < FrameMap::nof_xmm_regs; n++) {
-        VMReg xmm_name_0 = as_XMMRegister(n)->as_VMReg();
-        map->set_callee_saved(VMRegImpl::stack2reg(xmm_off +     num_rt_args), xmm_name_0);
-        // %%% This is really a waste but we'll keep things as they were for now
-        if (true) {
-          map->set_callee_saved(VMRegImpl::stack2reg(xmm_off + 1 + num_rt_args), xmm_name_0->next());
+        if (n < xmm_bypass_limit) {
+          VMReg xmm_name_0 = as_XMMRegister(n)->as_VMReg();
+          map->set_callee_saved(VMRegImpl::stack2reg(xmm_off + num_rt_args), xmm_name_0);
+          // %%% This is really a waste but we'll keep things as they were for now
+          if (true) {
+            map->set_callee_saved(VMRegImpl::stack2reg(xmm_off + 1 + num_rt_args), xmm_name_0->next());
+          }
         }
         xmm_off += 2;
       }
@@ -393,8 +402,10 @@
     } else if (UseSSE == 1) {
       int xmm_off = xmm_regs_as_doubles_off;
       for (int n = 0; n < FrameMap::nof_xmm_regs; n++) {
-        VMReg xmm_name_0 = as_XMMRegister(n)->as_VMReg();
-        map->set_callee_saved(VMRegImpl::stack2reg(xmm_off +     num_rt_args), xmm_name_0);
+        if (n < xmm_bypass_limit) {
+          VMReg xmm_name_0 = as_XMMRegister(n)->as_VMReg();
+          map->set_callee_saved(VMRegImpl::stack2reg(xmm_off + num_rt_args), xmm_name_0);
+        }
         xmm_off += 2;
       }
       assert(xmm_off == float_regs_as_doubles_off, "incorrect number of xmm registers");
@@ -474,6 +485,24 @@
       __ movdbl(Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 104), xmm13);
       __ movdbl(Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 112), xmm14);
       __ movdbl(Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 120), xmm15);
+      if (UseAVX > 2) {
+        __ movdbl(Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 128), xmm16);
+        __ movdbl(Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 136), xmm17);
+        __ movdbl(Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 144), xmm18);
+        __ movdbl(Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 152), xmm19);
+        __ movdbl(Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 160), xmm20);
+        __ movdbl(Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 168), xmm21);
+        __ movdbl(Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 176), xmm22);
+        __ movdbl(Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 184), xmm23);
+        __ movdbl(Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 192), xmm24);
+        __ movdbl(Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 200), xmm25);
+        __ movdbl(Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 208), xmm26);
+        __ movdbl(Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 216), xmm27);
+        __ movdbl(Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 224), xmm28);
+        __ movdbl(Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 232), xmm29);
+        __ movdbl(Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 240), xmm30);
+        __ movdbl(Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 248), xmm31);
+      }
 #endif // _LP64
     } else if (UseSSE == 1) {
       // save XMM registers as float because double not supported without SSE2
@@ -516,6 +545,24 @@
       __ movdbl(xmm13, Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 104));
       __ movdbl(xmm14, Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 112));
       __ movdbl(xmm15, Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 120));
+      if (UseAVX > 2) {
+        __ movdbl(xmm16, Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 128));
+        __ movdbl(xmm17, Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 136));
+        __ movdbl(xmm18, Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 144));
+        __ movdbl(xmm19, Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 152));
+        __ movdbl(xmm20, Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 160));
+        __ movdbl(xmm21, Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 168));
+        __ movdbl(xmm22, Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 176));
+        __ movdbl(xmm23, Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 184));
+        __ movdbl(xmm24, Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 192));
+        __ movdbl(xmm25, Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 200));
+        __ movdbl(xmm26, Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 208));
+        __ movdbl(xmm27, Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 216));
+        __ movdbl(xmm28, Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 224));
+        __ movdbl(xmm29, Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 232));
+        __ movdbl(xmm30, Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 240));
+        __ movdbl(xmm31, Address(rsp, xmm_regs_as_doubles_off * VMRegImpl::stack_slot_size + 248));
+      }
 #endif // _LP64
     } else if (UseSSE == 1) {
       // restore XMM registers
@@ -1631,36 +1678,22 @@
 
         NOT_LP64(__ get_thread(thread);)
 
-        Address in_progress(thread, in_bytes(JavaThread::satb_mark_queue_offset() +
-                                             PtrQueue::byte_offset_of_active()));
-
         Address queue_index(thread, in_bytes(JavaThread::satb_mark_queue_offset() +
                                              PtrQueue::byte_offset_of_index()));
         Address buffer(thread, in_bytes(JavaThread::satb_mark_queue_offset() +
                                         PtrQueue::byte_offset_of_buf()));
 
-
         Label done;
         Label runtime;
 
         // Can we store original value in the thread's buffer?
 
-#ifdef _LP64
-        __ movslq(tmp, queue_index);
-        __ cmpq(tmp, 0);
-#else
-        __ cmpl(queue_index, 0);
-#endif
-        __ jcc(Assembler::equal, runtime);
-#ifdef _LP64
-        __ subq(tmp, wordSize);
-        __ movl(queue_index, tmp);
-        __ addq(tmp, buffer);
-#else
-        __ subl(queue_index, wordSize);
-        __ movl(tmp, buffer);
-        __ addl(tmp, queue_index);
-#endif
+        __ movptr(tmp, queue_index);
+        __ testptr(tmp, tmp);
+        __ jcc(Assembler::zero, runtime);
+        __ subptr(tmp, wordSize);
+        __ movptr(queue_index, tmp);
+        __ addptr(tmp, buffer);
 
         // prev_val (rax)
         f.load_argument(0, pre_val);
@@ -1713,6 +1746,7 @@
         assert(sizeof(*ct->byte_map_base) == sizeof(jbyte), "adjust this code");
 
         Label done;
+        Label enqueued;
         Label runtime;
 
         // At this point we know new_value is non-NULL and the new_value crosses regions.
@@ -1752,28 +1786,19 @@
 
         __ movb(Address(card_addr, 0), (int)CardTableModRefBS::dirty_card_val());
 
-        __ cmpl(queue_index, 0);
-        __ jcc(Assembler::equal, runtime);
-        __ subl(queue_index, wordSize);
-
-        const Register buffer_addr = rbx;
-        __ push(rbx);
-
-        __ movptr(buffer_addr, buffer);
+        const Register tmp = rdx;
+        __ push(rdx);
 
-#ifdef _LP64
-        __ movslq(rscratch1, queue_index);
-        __ addptr(buffer_addr, rscratch1);
-#else
-        __ addptr(buffer_addr, queue_index);
-#endif
-        __ movptr(Address(buffer_addr, 0), card_addr);
-
-        __ pop(rbx);
-        __ jmp(done);
+        __ movptr(tmp, queue_index);
+        __ testptr(tmp, tmp);
+        __ jcc(Assembler::zero, runtime);
+        __ subptr(tmp, wordSize);
+        __ movptr(queue_index, tmp);
+        __ addptr(tmp, buffer);
+        __ movptr(Address(tmp, 0), card_addr);
+        __ jmp(enqueued);
 
         __ bind(runtime);
-        __ push(rdx);
 #ifdef _LP64
         __ push(r8);
         __ push(r9);
@@ -1795,12 +1820,12 @@
         __ pop(r9);
         __ pop(r8);
 #endif
+        __ bind(enqueued);
         __ pop(rdx);
+
         __ bind(done);
-
         __ pop(rcx);
         __ pop(rax);
-
       }
       break;
 #endif // INCLUDE_ALL_GCS
--- a/hotspot/src/cpu/x86/vm/c2_init_x86.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/c2_init_x86.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -25,6 +25,7 @@
 #include "precompiled.hpp"
 #include "opto/compile.hpp"
 #include "opto/node.hpp"
+#include "opto/optoreg.hpp"
 
 // processor dependent initialization for i486
 
@@ -37,4 +38,24 @@
     ConditionalMoveLimit = 0;
   }
 #endif // AMD64
+
+  if (UseAVX < 3) {
+    int delta = XMMRegisterImpl::max_slots_per_register * XMMRegisterImpl::number_of_registers;
+    int bottom = ConcreteRegisterImpl::max_fpr;
+    int top = bottom + delta;
+    int middle = bottom + (delta / 2);
+    int xmm_slots = XMMRegisterImpl::max_slots_per_register;
+    int lower = xmm_slots / 2;
+    // mark bad every register that we cannot get to if AVX less than 3, we have all slots in the array
+    // Note: vm2opto is allocated to ConcreteRegisterImpl::number_of_registers
+    for (int i = bottom; i < middle; i += xmm_slots) {
+      for (OptoReg::Name j = OptoReg::Name(i + lower); j<OptoReg::Name(i + xmm_slots); j = OptoReg::add(j, 1)) {
+        OptoReg::invalidate(j);
+      }
+    }
+    // mark the upper zmm bank bad and all the mask registers bad in this case
+    for (OptoReg::Name i = OptoReg::Name(middle); i<OptoReg::Name(_last_Mach_Reg - 1); i = OptoReg::add(i, 1)) {
+      OptoReg::invalidate(i);
+    }
+  }
 }
--- a/hotspot/src/cpu/x86/vm/frame_x86.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/frame_x86.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -125,7 +125,7 @@
     // Entry frames
 #ifdef AMD64
 #ifdef _WIN64
-    entry_frame_after_call_words                     =  28,
+    entry_frame_after_call_words                     =  60,
     entry_frame_call_wrapper_offset                  =  2,
 
     arg_reg_save_area_bytes                          = 32 // Register argument save area
--- a/hotspot/src/cpu/x86/vm/macroAssembler_x86.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/macroAssembler_x86.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -3996,21 +3996,21 @@
   }
 }
 
-void MacroAssembler::vandpd(XMMRegister dst, XMMRegister nds, AddressLiteral src, bool vector256) {
+void MacroAssembler::vandpd(XMMRegister dst, XMMRegister nds, AddressLiteral src, int vector_len) {
   if (reachable(src)) {
-    vandpd(dst, nds, as_Address(src), vector256);
+    vandpd(dst, nds, as_Address(src), vector_len);
   } else {
     lea(rscratch1, src);
-    vandpd(dst, nds, Address(rscratch1, 0), vector256);
-  }
-}
-
-void MacroAssembler::vandps(XMMRegister dst, XMMRegister nds, AddressLiteral src, bool vector256) {
+    vandpd(dst, nds, Address(rscratch1, 0), vector_len);
+  }
+}
+
+void MacroAssembler::vandps(XMMRegister dst, XMMRegister nds, AddressLiteral src, int vector_len) {
   if (reachable(src)) {
-    vandps(dst, nds, as_Address(src), vector256);
+    vandps(dst, nds, as_Address(src), vector_len);
   } else {
     lea(rscratch1, src);
-    vandps(dst, nds, Address(rscratch1, 0), vector256);
+    vandps(dst, nds, Address(rscratch1, 0), vector_len);
   }
 }
 
@@ -4068,21 +4068,21 @@
   }
 }
 
-void MacroAssembler::vxorpd(XMMRegister dst, XMMRegister nds, AddressLiteral src, bool vector256) {
+void MacroAssembler::vxorpd(XMMRegister dst, XMMRegister nds, AddressLiteral src, int vector_len) {
   if (reachable(src)) {
-    vxorpd(dst, nds, as_Address(src), vector256);
+    vxorpd(dst, nds, as_Address(src), vector_len);
   } else {
     lea(rscratch1, src);
-    vxorpd(dst, nds, Address(rscratch1, 0), vector256);
-  }
-}
-
-void MacroAssembler::vxorps(XMMRegister dst, XMMRegister nds, AddressLiteral src, bool vector256) {
+    vxorpd(dst, nds, Address(rscratch1, 0), vector_len);
+  }
+}
+
+void MacroAssembler::vxorps(XMMRegister dst, XMMRegister nds, AddressLiteral src, int vector_len) {
   if (reachable(src)) {
-    vxorps(dst, nds, as_Address(src), vector256);
+    vxorps(dst, nds, as_Address(src), vector_len);
   } else {
     lea(rscratch1, src);
-    vxorps(dst, nds, Address(rscratch1, 0), vector256);
+    vxorps(dst, nds, Address(rscratch1, 0), vector_len);
   }
 }
 
@@ -4561,6 +4561,14 @@
     movflt(Address(rsp,off++*sizeof(jdouble)),xmm6);
     movflt(Address(rsp,off++*sizeof(jdouble)),xmm7);
   } else if (UseSSE >= 2)  {
+    if (UseAVX > 2) {
+      movl(rbx, 0xffff);
+#ifdef _LP64
+      kmovql(k1, rbx);
+#else
+      kmovdl(k1, rbx);
+#endif
+    }
 #ifdef COMPILER2
     if (MaxVectorSize > 16) {
       assert(UseAVX > 0, "256bit vectors are supported only with AVX");
@@ -7063,8 +7071,39 @@
     {
       assert( UseSSE >= 2, "supported cpu only" );
       Label L_fill_32_bytes_loop, L_check_fill_8_bytes, L_fill_8_bytes_loop, L_fill_8_bytes;
+      if (UseAVX > 2) {
+        movl(rtmp, 0xffff);
+#ifdef _LP64
+        kmovql(k1, rtmp);
+#else
+        kmovdl(k1, rtmp);
+#endif
+      }
       movdl(xtmp, value);
-      if (UseAVX >= 2 && UseUnalignedLoadStores) {
+      if (UseAVX > 2 && UseUnalignedLoadStores) {
+        // Fill 64-byte chunks
+        Label L_fill_64_bytes_loop, L_check_fill_32_bytes;
+        evpbroadcastd(xtmp, xtmp, Assembler::AVX_512bit);
+
+        subl(count, 16 << shift);
+        jcc(Assembler::less, L_check_fill_32_bytes);
+        align(16);
+
+        BIND(L_fill_64_bytes_loop);
+        evmovdqu(Address(to, 0), xtmp, Assembler::AVX_512bit);
+        addptr(to, 64);
+        subl(count, 16 << shift);
+        jcc(Assembler::greaterEqual, L_fill_64_bytes_loop);
+
+        BIND(L_check_fill_32_bytes);
+        addl(count, 8 << shift);
+        jccb(Assembler::less, L_check_fill_8_bytes);
+        evmovdqu(Address(to, 0), xtmp, Assembler::AVX_256bit);
+        addptr(to, 32);
+        subl(count, 8 << shift);
+
+        BIND(L_check_fill_8_bytes);
+      } else if (UseAVX == 2 && UseUnalignedLoadStores) {
         // Fill 64-byte chunks
         Label L_fill_64_bytes_loop, L_check_fill_32_bytes;
         vpbroadcastd(xtmp, xtmp);
@@ -7200,11 +7239,11 @@
       bind(L_copy_32_chars);
       vmovdqu(tmp3Reg, Address(src, len, Address::times_2, -64));
       vmovdqu(tmp4Reg, Address(src, len, Address::times_2, -32));
-      vpor(tmp2Reg, tmp3Reg, tmp4Reg, /* vector256 */ true);
+      vpor(tmp2Reg, tmp3Reg, tmp4Reg, /* vector_len */ 1);
       vptest(tmp2Reg, tmp1Reg);       // check for Unicode chars in  vector
       jccb(Assembler::notZero, L_copy_32_chars_exit);
-      vpackuswb(tmp3Reg, tmp3Reg, tmp4Reg, /* vector256 */ true);
-      vpermq(tmp4Reg, tmp3Reg, 0xD8, /* vector256 */ true);
+      vpackuswb(tmp3Reg, tmp3Reg, tmp4Reg, /* vector_len */ 1);
+      vpermq(tmp4Reg, tmp3Reg, 0xD8, /* vector_len */ 1);
       vmovdqu(Address(dst, len, Address::times_1, -32), tmp4Reg);
 
       bind(L_chars_32_check);
@@ -7227,13 +7266,13 @@
       vmovdqu(tmp2Reg, Address(src, len, Address::times_2, -32));
       vptest(tmp2Reg, tmp1Reg);
       jccb(Assembler::notZero, L_copy_16_chars_exit);
-      vpackuswb(tmp2Reg, tmp2Reg, tmp1Reg, /* vector256 */ true);
-      vpermq(tmp3Reg, tmp2Reg, 0xD8, /* vector256 */ true);
+      vpackuswb(tmp2Reg, tmp2Reg, tmp1Reg, /* vector_len */ 1);
+      vpermq(tmp3Reg, tmp2Reg, 0xD8, /* vector_len */ 1);
     } else {
       if (UseAVX > 0) {
         movdqu(tmp3Reg, Address(src, len, Address::times_2, -32));
         movdqu(tmp4Reg, Address(src, len, Address::times_2, -16));
-        vpor(tmp2Reg, tmp3Reg, tmp4Reg, /* vector256 */ false);
+        vpor(tmp2Reg, tmp3Reg, tmp4Reg, /* vector_len */ 0);
       } else {
         movdqu(tmp3Reg, Address(src, len, Address::times_2, -32));
         por(tmp2Reg, tmp3Reg);
@@ -7776,7 +7815,7 @@
   if (UseAVX > 0) {
     vpclmulhdq(xtmp, xK, xcrc); // [123:64]
     vpclmulldq(xcrc, xK, xcrc); // [63:0]
-    vpxor(xcrc, xcrc, Address(buf, offset), false /* vector256 */);
+    vpxor(xcrc, xcrc, Address(buf, offset), 0 /* vector_len */);
     pxor(xcrc, xtmp);
   } else {
     movdqa(xtmp, xcrc);
@@ -7920,7 +7959,7 @@
   movdqu(xmm0, ExternalAddress(StubRoutines::x86::crc_by128_masks_addr()));
   if (UseAVX > 0) {
     vpclmulqdq(xmm2, xmm0, xmm1, 0x1);
-    vpand(xmm3, xmm0, xmm2, false /* vector256 */);
+    vpand(xmm3, xmm0, xmm2, 0 /* vector_len */);
     vpclmulqdq(xmm0, xmm0, xmm3, 0x1);
   } else {
     movdqa(xmm2, xmm0);
--- a/hotspot/src/cpu/x86/vm/macroAssembler_x86.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/macroAssembler_x86.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1024,13 +1024,13 @@
   void vaddss(XMMRegister dst, XMMRegister nds, Address src)     { Assembler::vaddss(dst, nds, src); }
   void vaddss(XMMRegister dst, XMMRegister nds, AddressLiteral src);
 
-  void vandpd(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) { Assembler::vandpd(dst, nds, src, vector256); }
-  void vandpd(XMMRegister dst, XMMRegister nds, Address src, bool vector256)     { Assembler::vandpd(dst, nds, src, vector256); }
-  void vandpd(XMMRegister dst, XMMRegister nds, AddressLiteral src, bool vector256);
+  void vandpd(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) { Assembler::vandpd(dst, nds, src, vector_len); }
+  void vandpd(XMMRegister dst, XMMRegister nds, Address src, int vector_len)     { Assembler::vandpd(dst, nds, src, vector_len); }
+  void vandpd(XMMRegister dst, XMMRegister nds, AddressLiteral src, int vector_len);
 
-  void vandps(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) { Assembler::vandps(dst, nds, src, vector256); }
-  void vandps(XMMRegister dst, XMMRegister nds, Address src, bool vector256)     { Assembler::vandps(dst, nds, src, vector256); }
-  void vandps(XMMRegister dst, XMMRegister nds, AddressLiteral src, bool vector256);
+  void vandps(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) { Assembler::vandps(dst, nds, src, vector_len); }
+  void vandps(XMMRegister dst, XMMRegister nds, Address src, int vector_len)     { Assembler::vandps(dst, nds, src, vector_len); }
+  void vandps(XMMRegister dst, XMMRegister nds, AddressLiteral src, int vector_len);
 
   void vdivsd(XMMRegister dst, XMMRegister nds, XMMRegister src) { Assembler::vdivsd(dst, nds, src); }
   void vdivsd(XMMRegister dst, XMMRegister nds, Address src)     { Assembler::vdivsd(dst, nds, src); }
@@ -1058,25 +1058,25 @@
 
   // AVX Vector instructions
 
-  void vxorpd(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) { Assembler::vxorpd(dst, nds, src, vector256); }
-  void vxorpd(XMMRegister dst, XMMRegister nds, Address src, bool vector256) { Assembler::vxorpd(dst, nds, src, vector256); }
-  void vxorpd(XMMRegister dst, XMMRegister nds, AddressLiteral src, bool vector256);
+  void vxorpd(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) { Assembler::vxorpd(dst, nds, src, vector_len); }
+  void vxorpd(XMMRegister dst, XMMRegister nds, Address src, int vector_len) { Assembler::vxorpd(dst, nds, src, vector_len); }
+  void vxorpd(XMMRegister dst, XMMRegister nds, AddressLiteral src, int vector_len);
 
-  void vxorps(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) { Assembler::vxorps(dst, nds, src, vector256); }
-  void vxorps(XMMRegister dst, XMMRegister nds, Address src, bool vector256) { Assembler::vxorps(dst, nds, src, vector256); }
-  void vxorps(XMMRegister dst, XMMRegister nds, AddressLiteral src, bool vector256);
+  void vxorps(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) { Assembler::vxorps(dst, nds, src, vector_len); }
+  void vxorps(XMMRegister dst, XMMRegister nds, Address src, int vector_len) { Assembler::vxorps(dst, nds, src, vector_len); }
+  void vxorps(XMMRegister dst, XMMRegister nds, AddressLiteral src, int vector_len);
 
-  void vpxor(XMMRegister dst, XMMRegister nds, XMMRegister src, bool vector256) {
-    if (UseAVX > 1 || !vector256) // vpxor 256 bit is available only in AVX2
-      Assembler::vpxor(dst, nds, src, vector256);
+  void vpxor(XMMRegister dst, XMMRegister nds, XMMRegister src, int vector_len) {
+    if (UseAVX > 1 || (vector_len < 1)) // vpxor 256 bit is available only in AVX2
+      Assembler::vpxor(dst, nds, src, vector_len);
     else
-      Assembler::vxorpd(dst, nds, src, vector256);
+      Assembler::vxorpd(dst, nds, src, vector_len);
   }
-  void vpxor(XMMRegister dst, XMMRegister nds, Address src, bool vector256) {
-    if (UseAVX > 1 || !vector256) // vpxor 256 bit is available only in AVX2
-      Assembler::vpxor(dst, nds, src, vector256);
+  void vpxor(XMMRegister dst, XMMRegister nds, Address src, int vector_len) {
+    if (UseAVX > 1 || (vector_len < 1)) // vpxor 256 bit is available only in AVX2
+      Assembler::vpxor(dst, nds, src, vector_len);
     else
-      Assembler::vxorpd(dst, nds, src, vector256);
+      Assembler::vxorpd(dst, nds, src, vector_len);
   }
 
   // Simple version for AVX2 256bit vectors
--- a/hotspot/src/cpu/x86/vm/register_definitions_x86.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/register_definitions_x86.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -68,6 +68,22 @@
 REGISTER_DEFINITION(XMMRegister, xmm13);
 REGISTER_DEFINITION(XMMRegister, xmm14);
 REGISTER_DEFINITION(XMMRegister, xmm15);
+REGISTER_DEFINITION(XMMRegister, xmm16);
+REGISTER_DEFINITION(XMMRegister, xmm17);
+REGISTER_DEFINITION(XMMRegister, xmm18);
+REGISTER_DEFINITION(XMMRegister, xmm19);
+REGISTER_DEFINITION(XMMRegister, xmm20);
+REGISTER_DEFINITION(XMMRegister, xmm21);
+REGISTER_DEFINITION(XMMRegister, xmm22);
+REGISTER_DEFINITION(XMMRegister, xmm23);
+REGISTER_DEFINITION(XMMRegister, xmm24);
+REGISTER_DEFINITION(XMMRegister, xmm25);
+REGISTER_DEFINITION(XMMRegister, xmm26);
+REGISTER_DEFINITION(XMMRegister, xmm27);
+REGISTER_DEFINITION(XMMRegister, xmm28);
+REGISTER_DEFINITION(XMMRegister, xmm29);
+REGISTER_DEFINITION(XMMRegister, xmm30);
+REGISTER_DEFINITION(XMMRegister, xmm31);
 
 REGISTER_DEFINITION(Register, c_rarg0);
 REGISTER_DEFINITION(Register, c_rarg1);
@@ -123,5 +139,15 @@
 REGISTER_DEFINITION(MMXRegister, mmx6 );
 REGISTER_DEFINITION(MMXRegister, mmx7 );
 
+REGISTER_DEFINITION(KRegister, knoreg);
+REGISTER_DEFINITION(KRegister, k0);
+REGISTER_DEFINITION(KRegister, k1);
+REGISTER_DEFINITION(KRegister, k2);
+REGISTER_DEFINITION(KRegister, k3);
+REGISTER_DEFINITION(KRegister, k4);
+REGISTER_DEFINITION(KRegister, k5);
+REGISTER_DEFINITION(KRegister, k6);
+REGISTER_DEFINITION(KRegister, k7);
+
 // JSR 292
 REGISTER_DEFINITION(Register, rbp_mh_SP_save);
--- a/hotspot/src/cpu/x86/vm/register_x86.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/register_x86.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -31,11 +31,13 @@
 const int ConcreteRegisterImpl::max_gpr = RegisterImpl::number_of_registers << 1;
 #endif // AMD64
 
+const int ConcreteRegisterImpl::max_fpr = ConcreteRegisterImpl::max_gpr +
+    2 * FloatRegisterImpl::number_of_registers;
+const int ConcreteRegisterImpl::max_xmm = ConcreteRegisterImpl::max_fpr +
+    XMMRegisterImpl::max_slots_per_register * XMMRegisterImpl::number_of_registers;
+const int ConcreteRegisterImpl::max_kpr = ConcreteRegisterImpl::max_xmm +
+    KRegisterImpl::max_slots_per_register * KRegisterImpl::number_of_registers;
 
-const int ConcreteRegisterImpl::max_fpr = ConcreteRegisterImpl::max_gpr +
-                                                                 2 * FloatRegisterImpl::number_of_registers;
-const int ConcreteRegisterImpl::max_xmm = ConcreteRegisterImpl::max_fpr +
-                                                                 8 * XMMRegisterImpl::number_of_registers;
 const char* RegisterImpl::name() const {
   const char* names[number_of_registers] = {
 #ifndef AMD64
@@ -59,8 +61,17 @@
   const char* names[number_of_registers] = {
     "xmm0","xmm1","xmm2","xmm3","xmm4","xmm5","xmm6","xmm7"
 #ifdef AMD64
-    ,"xmm8",  "xmm9", "xmm10", "xmm11", "xmm12", "xmm13", "xmm14", "xmm15"
+    ,"xmm8",   "xmm9",  "xmm10", "xmm11", "xmm12", "xmm13", "xmm14", "xmm15"
+    ,"xmm16",  "xmm17", "xmm18", "xmm19", "xmm20", "xmm21", "xmm22", "xmm23"
+    ,"xmm24",  "xmm25", "xmm26", "xmm27", "xmm28", "xmm29", "xmm30", "xmm31"
 #endif // AMD64
   };
   return is_valid() ? names[encoding()] : "xnoreg";
 }
+
+const char* KRegisterImpl::name() const {
+  const char* names[number_of_registers] = {
+    "k0", "k1", "k2", "k3", "k4", "k5", "k6", "k7"
+  };
+  return is_valid() ? names[encoding()] : "knoreg";
+}
--- a/hotspot/src/cpu/x86/vm/register_x86.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/register_x86.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -45,10 +45,12 @@
   enum {
 #ifndef AMD64
     number_of_registers      = 8,
-    number_of_byte_registers = 4
+    number_of_byte_registers = 4,
+    max_slots_per_register   = 1
 #else
     number_of_registers      = 16,
-    number_of_byte_registers = 16
+    number_of_byte_registers = 16,
+    max_slots_per_register   = 1
 #endif // AMD64
   };
 
@@ -143,9 +145,11 @@
  public:
   enum {
 #ifndef AMD64
-    number_of_registers = 8
+    number_of_registers = 8,
+    max_slots_per_register = 16   // 512-bit
 #else
-    number_of_registers = 16
+    number_of_registers = 32,
+    max_slots_per_register = 16   // 512-bit
 #endif // AMD64
   };
 
@@ -183,6 +187,22 @@
 CONSTANT_REGISTER_DECLARATION(XMMRegister, xmm13,    (13));
 CONSTANT_REGISTER_DECLARATION(XMMRegister, xmm14,    (14));
 CONSTANT_REGISTER_DECLARATION(XMMRegister, xmm15,    (15));
+CONSTANT_REGISTER_DECLARATION(XMMRegister, xmm16,    (16));
+CONSTANT_REGISTER_DECLARATION(XMMRegister, xmm17,    (17));
+CONSTANT_REGISTER_DECLARATION(XMMRegister, xmm18,    (18));
+CONSTANT_REGISTER_DECLARATION(XMMRegister, xmm19,    (19));
+CONSTANT_REGISTER_DECLARATION(XMMRegister, xmm20,    (20));
+CONSTANT_REGISTER_DECLARATION(XMMRegister, xmm21,    (21));
+CONSTANT_REGISTER_DECLARATION(XMMRegister, xmm22,    (22));
+CONSTANT_REGISTER_DECLARATION(XMMRegister, xmm23,    (23));
+CONSTANT_REGISTER_DECLARATION(XMMRegister, xmm24,    (24));
+CONSTANT_REGISTER_DECLARATION(XMMRegister, xmm25,    (25));
+CONSTANT_REGISTER_DECLARATION(XMMRegister, xmm26,    (26));
+CONSTANT_REGISTER_DECLARATION(XMMRegister, xmm27,    (27));
+CONSTANT_REGISTER_DECLARATION(XMMRegister, xmm28,    (28));
+CONSTANT_REGISTER_DECLARATION(XMMRegister, xmm29,    (29));
+CONSTANT_REGISTER_DECLARATION(XMMRegister, xmm30,    (30));
+CONSTANT_REGISTER_DECLARATION(XMMRegister, xmm31,    (31));
 #endif // AMD64
 
 // Only used by the 32bit stubGenerator. These can't be described by vmreg and hence
@@ -200,6 +220,46 @@
 CONSTANT_REGISTER_DECLARATION(MMXRegister, mmx6 , ( 6));
 CONSTANT_REGISTER_DECLARATION(MMXRegister, mmx7 , ( 7));
 
+// Use XMMRegister as shortcut
+class KRegisterImpl;
+typedef KRegisterImpl* KRegister;
+
+inline KRegister as_KRegister(int encoding) {
+  return (KRegister)(intptr_t)encoding;
+}
+
+// The implementation of XMM registers for the IA32 architecture
+class KRegisterImpl : public AbstractRegisterImpl {
+public:
+  enum {
+    number_of_registers = 8,
+    max_slots_per_register = 1
+  };
+
+  // construction
+  friend KRegister as_KRegister(int encoding);
+
+  inline VMReg as_VMReg();
+
+  // derived registers, offsets, and addresses
+  KRegister successor() const                          { return as_KRegister(encoding() + 1); }
+
+  // accessors
+  int   encoding() const                          { assert(is_valid(), err_msg("invalid register (%d)", (int)(intptr_t)this)); return (intptr_t)this; }
+  bool  is_valid() const                          { return 0 <= (intptr_t)this && (intptr_t)this < number_of_registers; }
+  const char* name() const;
+};
+
+// The Mask registers, for AVX3 enabled and up chips
+CONSTANT_REGISTER_DECLARATION(KRegister, knoreg, (-1));
+CONSTANT_REGISTER_DECLARATION(KRegister, k0, (0));
+CONSTANT_REGISTER_DECLARATION(KRegister, k1, (1));
+CONSTANT_REGISTER_DECLARATION(KRegister, k2, (2));
+CONSTANT_REGISTER_DECLARATION(KRegister, k3, (3));
+CONSTANT_REGISTER_DECLARATION(KRegister, k4, (4));
+CONSTANT_REGISTER_DECLARATION(KRegister, k5, (5));
+CONSTANT_REGISTER_DECLARATION(KRegister, k6, (6));
+CONSTANT_REGISTER_DECLARATION(KRegister, k7, (7));
 
 // Need to know the total number of registers of all sorts for SharedInfo.
 // Define a class that exports it.
@@ -211,18 +271,20 @@
   // There is no requirement that any ordering here matches any ordering c2 gives
   // it's optoregs.
 
-    number_of_registers =      RegisterImpl::number_of_registers +
+    number_of_registers = RegisterImpl::number_of_registers +
 #ifdef AMD64
-                               RegisterImpl::number_of_registers +  // "H" half of a 64bit register
+      RegisterImpl::number_of_registers +  // "H" half of a 64bit register
 #endif // AMD64
-                           2 * FloatRegisterImpl::number_of_registers +
-                           8 * XMMRegisterImpl::number_of_registers +
-                           1 // eflags
+      2 * FloatRegisterImpl::number_of_registers +
+      XMMRegisterImpl::max_slots_per_register * XMMRegisterImpl::number_of_registers +
+      KRegisterImpl::number_of_registers + // mask registers
+      1 // eflags
   };
 
   static const int max_gpr;
   static const int max_fpr;
   static const int max_xmm;
+  static const int max_kpr;
 
 };
 
--- a/hotspot/src/cpu/x86/vm/sharedRuntime_x86_32.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/sharedRuntime_x86_32.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -117,9 +117,9 @@
   int vect_words = 0;
 #ifdef COMPILER2
   if (save_vectors) {
-    assert(UseAVX > 0, "256bit vectors are supported only with AVX");
-    assert(MaxVectorSize == 32, "only 256bit vectors are supported now");
-    // Save upper half of YMM registes
+    assert(UseAVX > 0, "512bit vectors are supported only with EVEX");
+    assert(MaxVectorSize == 64, "only 512bit vectors are supported now");
+    // Save upper half of ZMM/YMM registers :
     vect_words = 8 * 16 / wordSize;
     additional_frame_words += vect_words;
   }
@@ -216,6 +216,17 @@
     __ vextractf128h(Address(rsp, 80),xmm5);
     __ vextractf128h(Address(rsp, 96),xmm6);
     __ vextractf128h(Address(rsp,112),xmm7);
+    if (UseAVX > 2) {
+      __ subptr(rsp, 256); // Save upper half of ZMM registes
+      __ vextractf64x4h(Address(rsp, 0), xmm0);
+      __ vextractf64x4h(Address(rsp, 32), xmm1);
+      __ vextractf64x4h(Address(rsp, 64), xmm2);
+      __ vextractf64x4h(Address(rsp, 96), xmm3);
+      __ vextractf64x4h(Address(rsp, 128), xmm4);
+      __ vextractf64x4h(Address(rsp, 160), xmm5);
+      __ vextractf64x4h(Address(rsp, 192), xmm6);
+      __ vextractf64x4h(Address(rsp, 224), xmm7);
+    }
   }
 
   // Set an oopmap for the call site.  This oopmap will map all
@@ -283,8 +294,8 @@
   int additional_frame_bytes = 0;
 #ifdef COMPILER2
   if (restore_vectors) {
-    assert(UseAVX > 0, "256bit vectors are supported only with AVX");
-    assert(MaxVectorSize == 32, "only 256bit vectors are supported now");
+    assert(UseAVX > 0, "512bit vectors are supported only with EVEX");
+    assert(MaxVectorSize == 64, "only 512bit vectors are supported now");
     additional_frame_bytes = 128;
   }
 #else
@@ -324,6 +335,18 @@
     __ vinsertf128h(xmm6, Address(rsp, 96));
     __ vinsertf128h(xmm7, Address(rsp,112));
     __ addptr(rsp, additional_frame_bytes);
+    if (UseAVX > 2) {
+      additional_frame_bytes = 256;
+      __ vinsertf64x4h(xmm0, Address(rsp, 0));
+      __ vinsertf64x4h(xmm1, Address(rsp, 32));
+      __ vinsertf64x4h(xmm2, Address(rsp, 64));
+      __ vinsertf64x4h(xmm3, Address(rsp, 96));
+      __ vinsertf64x4h(xmm4, Address(rsp, 128));
+      __ vinsertf64x4h(xmm5, Address(rsp, 160));
+      __ vinsertf64x4h(xmm6, Address(rsp, 192));
+      __ vinsertf64x4h(xmm7, Address(rsp, 224));
+      __ addptr(rsp, additional_frame_bytes);
+    }
   }
   __ pop_FPU_state();
   __ addptr(rsp, FPU_regs_live*wordSize); // Pop FPU registers
--- a/hotspot/src/cpu/x86/vm/sharedRuntime_x86_64.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/sharedRuntime_x86_64.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -86,7 +86,23 @@
     DEF_XMM_OFFS(13),
     DEF_XMM_OFFS(14),
     DEF_XMM_OFFS(15),
-    fpu_state_end = fpu_state_off + ((FPUStateSizeInWords-1)*wordSize / BytesPerInt),
+    DEF_XMM_OFFS(16),
+    DEF_XMM_OFFS(17),
+    DEF_XMM_OFFS(18),
+    DEF_XMM_OFFS(19),
+    DEF_XMM_OFFS(20),
+    DEF_XMM_OFFS(21),
+    DEF_XMM_OFFS(22),
+    DEF_XMM_OFFS(23),
+    DEF_XMM_OFFS(24),
+    DEF_XMM_OFFS(25),
+    DEF_XMM_OFFS(26),
+    DEF_XMM_OFFS(27),
+    DEF_XMM_OFFS(28),
+    DEF_XMM_OFFS(29),
+    DEF_XMM_OFFS(30),
+    DEF_XMM_OFFS(31),
+    fpu_state_end = fpu_state_off + ((FPUStateSizeInWords - 1)*wordSize / BytesPerInt),
     fpu_stateH_end,
     r15_off, r15H_off,
     r14_off, r14H_off,
@@ -136,13 +152,21 @@
 
 OopMap* RegisterSaver::save_live_registers(MacroAssembler* masm, int additional_frame_words, int* total_frame_words, bool save_vectors) {
   int vect_words = 0;
+  int num_xmm_regs = 16;
+  if (UseAVX > 2) {
+    num_xmm_regs = 32;
+  }
 #ifdef COMPILER2
   if (save_vectors) {
-    assert(UseAVX > 0, "256bit vectors are supported only with AVX");
-    assert(MaxVectorSize == 32, "only 256bit vectors are supported now");
-    // Save upper half of YMM registes
-    vect_words = 16 * 16 / wordSize;
+    assert(UseAVX > 0, "512bit vectors are supported only with EVEX");
+    assert(MaxVectorSize == 64, "only 512bit vectors are supported now");
+    // Save upper half of YMM registers
+    vect_words = 16 * num_xmm_regs / wordSize;
     additional_frame_words += vect_words;
+    if (UseAVX > 2) {
+      // Save upper half of ZMM registers as well
+      additional_frame_words += vect_words;
+    }
   }
 #else
   assert(!save_vectors, "vectors are generated only by C2");
@@ -150,7 +174,7 @@
 
   // Always make the frame size 16-byte aligned
   int frame_size_in_bytes = round_to(additional_frame_words*wordSize +
-                                     reg_save_size*BytesPerInt, 16);
+                                     reg_save_size*BytesPerInt, num_xmm_regs);
   // OopMap frame size is in compiler stack slots (jint's) not bytes or words
   int frame_size_in_slots = frame_size_in_bytes / BytesPerInt;
   // The caller will allocate additional_frame_words
@@ -169,24 +193,77 @@
   __ push_CPU_state(); // Push a multiple of 16 bytes
 
   if (vect_words > 0) {
-    assert(vect_words*wordSize == 256, "");
-    __ subptr(rsp, 256); // Save upper half of YMM registes
-    __ vextractf128h(Address(rsp,  0),xmm0);
-    __ vextractf128h(Address(rsp, 16),xmm1);
-    __ vextractf128h(Address(rsp, 32),xmm2);
-    __ vextractf128h(Address(rsp, 48),xmm3);
-    __ vextractf128h(Address(rsp, 64),xmm4);
-    __ vextractf128h(Address(rsp, 80),xmm5);
-    __ vextractf128h(Address(rsp, 96),xmm6);
-    __ vextractf128h(Address(rsp,112),xmm7);
-    __ vextractf128h(Address(rsp,128),xmm8);
-    __ vextractf128h(Address(rsp,144),xmm9);
-    __ vextractf128h(Address(rsp,160),xmm10);
-    __ vextractf128h(Address(rsp,176),xmm11);
-    __ vextractf128h(Address(rsp,192),xmm12);
-    __ vextractf128h(Address(rsp,208),xmm13);
-    __ vextractf128h(Address(rsp,224),xmm14);
-    __ vextractf128h(Address(rsp,240),xmm15);
+    assert(vect_words*wordSize >= 256, "");
+    __ subptr(rsp, 256); // Save upper half of YMM registes(0..15)
+    __ vextractf128h(Address(rsp, 0), xmm0);
+    __ vextractf128h(Address(rsp, 16), xmm1);
+    __ vextractf128h(Address(rsp, 32), xmm2);
+    __ vextractf128h(Address(rsp, 48), xmm3);
+    __ vextractf128h(Address(rsp, 64), xmm4);
+    __ vextractf128h(Address(rsp, 80), xmm5);
+    __ vextractf128h(Address(rsp, 96), xmm6);
+    __ vextractf128h(Address(rsp, 112), xmm7);
+    __ vextractf128h(Address(rsp, 128), xmm8);
+    __ vextractf128h(Address(rsp, 144), xmm9);
+    __ vextractf128h(Address(rsp, 160), xmm10);
+    __ vextractf128h(Address(rsp, 176), xmm11);
+    __ vextractf128h(Address(rsp, 192), xmm12);
+    __ vextractf128h(Address(rsp, 208), xmm13);
+    __ vextractf128h(Address(rsp, 224), xmm14);
+    __ vextractf128h(Address(rsp, 240), xmm15);
+    if (UseAVX > 2) {
+      __ subptr(rsp, 256); // Save upper half of YMM registes(16..31)
+      __ vextractf128h(Address(rsp, 0), xmm16);
+      __ vextractf128h(Address(rsp, 16), xmm17);
+      __ vextractf128h(Address(rsp, 32), xmm18);
+      __ vextractf128h(Address(rsp, 48), xmm19);
+      __ vextractf128h(Address(rsp, 64), xmm20);
+      __ vextractf128h(Address(rsp, 80), xmm21);
+      __ vextractf128h(Address(rsp, 96), xmm22);
+      __ vextractf128h(Address(rsp, 112), xmm23);
+      __ vextractf128h(Address(rsp, 128), xmm24);
+      __ vextractf128h(Address(rsp, 144), xmm25);
+      __ vextractf128h(Address(rsp, 160), xmm26);
+      __ vextractf128h(Address(rsp, 176), xmm27);
+      __ vextractf128h(Address(rsp, 192), xmm28);
+      __ vextractf128h(Address(rsp, 208), xmm29);
+      __ vextractf128h(Address(rsp, 224), xmm30);
+      __ vextractf128h(Address(rsp, 240), xmm31);
+      // Now handle the ZMM registers (0..31)
+      __ subptr(rsp, 1024); // Save upper half of ZMM registes
+      __ vextractf64x4h(Address(rsp, 0), xmm0);
+      __ vextractf64x4h(Address(rsp, 32), xmm1);
+      __ vextractf64x4h(Address(rsp, 64), xmm2);
+      __ vextractf64x4h(Address(rsp, 96), xmm3);
+      __ vextractf64x4h(Address(rsp, 128), xmm4);
+      __ vextractf64x4h(Address(rsp, 160), xmm5);
+      __ vextractf64x4h(Address(rsp, 192), xmm6);
+      __ vextractf64x4h(Address(rsp, 224), xmm7);
+      __ vextractf64x4h(Address(rsp, 256), xmm8);
+      __ vextractf64x4h(Address(rsp, 288), xmm9);
+      __ vextractf64x4h(Address(rsp, 320), xmm10);
+      __ vextractf64x4h(Address(rsp, 352), xmm11);
+      __ vextractf64x4h(Address(rsp, 384), xmm12);
+      __ vextractf64x4h(Address(rsp, 416), xmm13);
+      __ vextractf64x4h(Address(rsp, 448), xmm14);
+      __ vextractf64x4h(Address(rsp, 480), xmm15);
+      __ vextractf64x4h(Address(rsp, 512), xmm16);
+      __ vextractf64x4h(Address(rsp, 544), xmm17);
+      __ vextractf64x4h(Address(rsp, 576), xmm18);
+      __ vextractf64x4h(Address(rsp, 608), xmm19);
+      __ vextractf64x4h(Address(rsp, 640), xmm20);
+      __ vextractf64x4h(Address(rsp, 672), xmm21);
+      __ vextractf64x4h(Address(rsp, 704), xmm22);
+      __ vextractf64x4h(Address(rsp, 736), xmm23);
+      __ vextractf64x4h(Address(rsp, 768), xmm24);
+      __ vextractf64x4h(Address(rsp, 800), xmm25);
+      __ vextractf64x4h(Address(rsp, 832), xmm26);
+      __ vextractf64x4h(Address(rsp, 864), xmm27);
+      __ vextractf64x4h(Address(rsp, 896), xmm28);
+      __ vextractf64x4h(Address(rsp, 928), xmm29);
+      __ vextractf64x4h(Address(rsp, 960), xmm30);
+      __ vextractf64x4h(Address(rsp, 992), xmm31);
+    }
   }
   if (frame::arg_reg_save_area_bytes != 0) {
     // Allocate argument register save area
@@ -235,6 +312,24 @@
   map->set_callee_saved(STACK_OFFSET(xmm13_off), xmm13->as_VMReg());
   map->set_callee_saved(STACK_OFFSET(xmm14_off), xmm14->as_VMReg());
   map->set_callee_saved(STACK_OFFSET(xmm15_off), xmm15->as_VMReg());
+  if (UseAVX > 2) {
+    map->set_callee_saved(STACK_OFFSET(xmm16_off), xmm16->as_VMReg());
+    map->set_callee_saved(STACK_OFFSET(xmm17_off), xmm17->as_VMReg());
+    map->set_callee_saved(STACK_OFFSET(xmm18_off), xmm18->as_VMReg());
+    map->set_callee_saved(STACK_OFFSET(xmm19_off), xmm19->as_VMReg());
+    map->set_callee_saved(STACK_OFFSET(xmm20_off), xmm20->as_VMReg());
+    map->set_callee_saved(STACK_OFFSET(xmm21_off), xmm21->as_VMReg());
+    map->set_callee_saved(STACK_OFFSET(xmm22_off), xmm22->as_VMReg());
+    map->set_callee_saved(STACK_OFFSET(xmm23_off), xmm23->as_VMReg());
+    map->set_callee_saved(STACK_OFFSET(xmm24_off), xmm24->as_VMReg());
+    map->set_callee_saved(STACK_OFFSET(xmm25_off), xmm25->as_VMReg());
+    map->set_callee_saved(STACK_OFFSET(xmm26_off), xmm26->as_VMReg());
+    map->set_callee_saved(STACK_OFFSET(xmm27_off), xmm27->as_VMReg());
+    map->set_callee_saved(STACK_OFFSET(xmm28_off), xmm28->as_VMReg());
+    map->set_callee_saved(STACK_OFFSET(xmm29_off), xmm29->as_VMReg());
+    map->set_callee_saved(STACK_OFFSET(xmm30_off), xmm30->as_VMReg());
+    map->set_callee_saved(STACK_OFFSET(xmm31_off), xmm31->as_VMReg());
+  }
 
   // %%% These should all be a waste but we'll keep things as they were for now
   if (true) {
@@ -269,6 +364,24 @@
     map->set_callee_saved(STACK_OFFSET(xmm13H_off), xmm13->as_VMReg()->next());
     map->set_callee_saved(STACK_OFFSET(xmm14H_off), xmm14->as_VMReg()->next());
     map->set_callee_saved(STACK_OFFSET(xmm15H_off), xmm15->as_VMReg()->next());
+    if (UseAVX > 2) {
+      map->set_callee_saved(STACK_OFFSET(xmm16H_off), xmm16->as_VMReg());
+      map->set_callee_saved(STACK_OFFSET(xmm17H_off), xmm17->as_VMReg());
+      map->set_callee_saved(STACK_OFFSET(xmm18H_off), xmm18->as_VMReg());
+      map->set_callee_saved(STACK_OFFSET(xmm19H_off), xmm19->as_VMReg());
+      map->set_callee_saved(STACK_OFFSET(xmm20H_off), xmm20->as_VMReg());
+      map->set_callee_saved(STACK_OFFSET(xmm21H_off), xmm21->as_VMReg());
+      map->set_callee_saved(STACK_OFFSET(xmm22H_off), xmm22->as_VMReg());
+      map->set_callee_saved(STACK_OFFSET(xmm23H_off), xmm23->as_VMReg());
+      map->set_callee_saved(STACK_OFFSET(xmm24H_off), xmm24->as_VMReg());
+      map->set_callee_saved(STACK_OFFSET(xmm25H_off), xmm25->as_VMReg());
+      map->set_callee_saved(STACK_OFFSET(xmm26H_off), xmm26->as_VMReg());
+      map->set_callee_saved(STACK_OFFSET(xmm27H_off), xmm27->as_VMReg());
+      map->set_callee_saved(STACK_OFFSET(xmm28H_off), xmm28->as_VMReg());
+      map->set_callee_saved(STACK_OFFSET(xmm29H_off), xmm29->as_VMReg());
+      map->set_callee_saved(STACK_OFFSET(xmm30H_off), xmm30->as_VMReg());
+      map->set_callee_saved(STACK_OFFSET(xmm31H_off), xmm31->as_VMReg());
+    }
   }
 
   return map;
@@ -281,9 +394,9 @@
   }
 #ifdef COMPILER2
   if (restore_vectors) {
-    // Restore upper half of YMM registes.
-    assert(UseAVX > 0, "256bit vectors are supported only with AVX");
-    assert(MaxVectorSize == 32, "only 256bit vectors are supported now");
+    // Restore upper half of YMM registes (0..15)
+    assert(UseAVX > 0, "512bit vectors are supported only with AVX");
+    assert(MaxVectorSize == 64, "only 512bit vectors are supported now");
     __ vinsertf128h(xmm0, Address(rsp,  0));
     __ vinsertf128h(xmm1, Address(rsp, 16));
     __ vinsertf128h(xmm2, Address(rsp, 32));
@@ -301,6 +414,60 @@
     __ vinsertf128h(xmm14, Address(rsp,224));
     __ vinsertf128h(xmm15, Address(rsp,240));
     __ addptr(rsp, 256);
+    if (UseAVX > 2) {
+      // Restore upper half of YMM registes (16..31)
+      __ vinsertf128h(xmm16, Address(rsp,  0));
+      __ vinsertf128h(xmm17, Address(rsp, 16));
+      __ vinsertf128h(xmm18, Address(rsp, 32));
+      __ vinsertf128h(xmm19, Address(rsp, 48));
+      __ vinsertf128h(xmm20, Address(rsp, 64));
+      __ vinsertf128h(xmm21, Address(rsp, 80));
+      __ vinsertf128h(xmm22, Address(rsp, 96));
+      __ vinsertf128h(xmm23, Address(rsp,112));
+      __ vinsertf128h(xmm24, Address(rsp,128));
+      __ vinsertf128h(xmm25, Address(rsp,144));
+      __ vinsertf128h(xmm26, Address(rsp,160));
+      __ vinsertf128h(xmm27, Address(rsp,176));
+      __ vinsertf128h(xmm28, Address(rsp,192));
+      __ vinsertf128h(xmm29, Address(rsp,208));
+      __ vinsertf128h(xmm30, Address(rsp,224));
+      __ vinsertf128h(xmm31, Address(rsp,240));
+      __ addptr(rsp, 256);
+      // Restore upper half of ZMM registes.
+      __ vinsertf64x4h(xmm0, Address(rsp, 0));
+      __ vinsertf64x4h(xmm1, Address(rsp, 32));
+      __ vinsertf64x4h(xmm2, Address(rsp, 64));
+      __ vinsertf64x4h(xmm3, Address(rsp, 96));
+      __ vinsertf64x4h(xmm4, Address(rsp, 128));
+      __ vinsertf64x4h(xmm5, Address(rsp, 160));
+      __ vinsertf64x4h(xmm6, Address(rsp, 192));
+      __ vinsertf64x4h(xmm7, Address(rsp, 224));
+      __ vinsertf64x4h(xmm8, Address(rsp, 256));
+      __ vinsertf64x4h(xmm9, Address(rsp, 288));
+      __ vinsertf64x4h(xmm10, Address(rsp, 320));
+      __ vinsertf64x4h(xmm11, Address(rsp, 352));
+      __ vinsertf64x4h(xmm12, Address(rsp, 384));
+      __ vinsertf64x4h(xmm13, Address(rsp, 416));
+      __ vinsertf64x4h(xmm14, Address(rsp, 448));
+      __ vinsertf64x4h(xmm15, Address(rsp, 480));
+      __ vinsertf64x4h(xmm16, Address(rsp, 512));
+      __ vinsertf64x4h(xmm17, Address(rsp, 544));
+      __ vinsertf64x4h(xmm18, Address(rsp, 576));
+      __ vinsertf64x4h(xmm19, Address(rsp, 608));
+      __ vinsertf64x4h(xmm20, Address(rsp, 640));
+      __ vinsertf64x4h(xmm21, Address(rsp, 672));
+      __ vinsertf64x4h(xmm22, Address(rsp, 704));
+      __ vinsertf64x4h(xmm23, Address(rsp, 736));
+      __ vinsertf64x4h(xmm24, Address(rsp, 768));
+      __ vinsertf64x4h(xmm25, Address(rsp, 800));
+      __ vinsertf64x4h(xmm26, Address(rsp, 832));
+      __ vinsertf64x4h(xmm27, Address(rsp, 864));
+      __ vinsertf64x4h(xmm28, Address(rsp, 896));
+      __ vinsertf64x4h(xmm29, Address(rsp, 928));
+      __ vinsertf64x4h(xmm30, Address(rsp, 960));
+      __ vinsertf64x4h(xmm31, Address(rsp, 992));
+      __ subptr(rsp, 1024);
+    }
   }
 #else
   assert(!restore_vectors, "vectors are generated only by C2");
--- a/hotspot/src/cpu/x86/vm/stubGenerator_x86_32.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/stubGenerator_x86_32.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -166,6 +166,13 @@
     __ movptr(saved_rdi, rdi);
     __ movptr(saved_rsi, rsi);
     __ movptr(saved_rbx, rbx);
+
+    // provide initial value for required masks
+    if (UseAVX > 2) {
+      __ movl(rbx, 0xffff);
+      __ kmovdl(k1, rbx);
+    }
+
     // save and initialize %mxcsr
     if (sse_save) {
       Label skip_ldmx;
@@ -794,7 +801,10 @@
   __ BIND(L_copy_64_bytes_loop);
 
     if (UseUnalignedLoadStores) {
-      if (UseAVX >= 2) {
+      if (UseAVX > 2) {
+        __ evmovdqu(xmm0, Address(from, 0), Assembler::AVX_512bit);
+        __ evmovdqu(Address(from, to_from, Address::times_1, 0), xmm0, Assembler::AVX_512bit);
+      } else if (UseAVX == 2) {
         __ vmovdqu(xmm0, Address(from,  0));
         __ vmovdqu(Address(from, to_from, Address::times_1,  0), xmm0);
         __ vmovdqu(xmm1, Address(from, 32));
@@ -833,7 +843,7 @@
     __ subl(qword_count, 8);
     __ jcc(Assembler::greaterEqual, L_copy_64_bytes_loop);
 
-    if (UseUnalignedLoadStores && (UseAVX >= 2)) {
+    if (UseUnalignedLoadStores && (UseAVX == 2)) {
       // clean upper bits of YMM registers
       __ vpxor(xmm0, xmm0);
       __ vpxor(xmm1, xmm1);
--- a/hotspot/src/cpu/x86/vm/stubGenerator_x86_64.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/stubGenerator_x86_64.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -137,8 +137,10 @@
   //     [ return_from_Java     ] <--- rsp
   //     [ argument word n      ]
   //      ...
-  // -28 [ argument word 1      ]
-  // -27 [ saved xmm15          ] <--- rsp_after_call
+  // -60 [ argument word 1      ]
+  // -59 [ saved xmm31          ] <--- rsp after_call
+  //     [ saved xmm16-xmm30    ] (EVEX enabled, else the space is blank)
+  // -27 [ saved xmm15          ]
   //     [ saved xmm7-xmm14     ]
   //  -9 [ saved xmm6           ] (each xmm register takes 2 slots)
   //  -7 [ saved r15            ]
@@ -166,7 +168,7 @@
   enum call_stub_layout {
 #ifdef _WIN64
     xmm_save_first     = 6,  // save from xmm6
-    xmm_save_last      = 15, // to xmm15
+    xmm_save_last      = 31, // to xmm31
     xmm_save_base      = -9,
     rsp_after_call_off = xmm_save_base - 2 * (xmm_save_last - xmm_save_first), // -27
     r15_off            = -7,
@@ -262,9 +264,19 @@
     __ movptr(r13_save, r13);
     __ movptr(r14_save, r14);
     __ movptr(r15_save, r15);
+    if (UseAVX > 2) {
+      __ movl(rbx, 0xffff);
+      __ kmovql(k1, rbx);
+    }
 #ifdef _WIN64
-    for (int i = 6; i <= 15; i++) {
-      __ movdqu(xmm_save(i), as_XMMRegister(i));
+    if (UseAVX > 2) {
+      for (int i = 6; i <= 31; i++) {
+        __ movdqu(xmm_save(i), as_XMMRegister(i));
+      }
+    } else {
+      for (int i = 6; i <= 15; i++) {
+        __ movdqu(xmm_save(i), as_XMMRegister(i));
+      }
     }
 
     const Address rdi_save(rbp, rdi_off * wordSize);
@@ -1318,7 +1330,10 @@
       Label L_end;
       // Copy 64-bytes per iteration
       __ BIND(L_loop);
-      if (UseAVX >= 2) {
+      if (UseAVX > 2) {
+        __ evmovdqu(xmm0, Address(end_from, qword_count, Address::times_8, -56), Assembler::AVX_512bit);
+        __ evmovdqu(Address(end_to, qword_count, Address::times_8, -56), xmm0, Assembler::AVX_512bit);
+      } else if (UseAVX == 2) {
         __ vmovdqu(xmm0, Address(end_from, qword_count, Address::times_8, -56));
         __ vmovdqu(Address(end_to, qword_count, Address::times_8, -56), xmm0);
         __ vmovdqu(xmm1, Address(end_from, qword_count, Address::times_8, -24));
@@ -1395,7 +1410,10 @@
       Label L_end;
       // Copy 64-bytes per iteration
       __ BIND(L_loop);
-      if (UseAVX >= 2) {
+      if (UseAVX > 2) {
+        __ evmovdqu(xmm0, Address(from, qword_count, Address::times_8, 32), Assembler::AVX_512bit);
+        __ evmovdqu(Address(dest, qword_count, Address::times_8, 32), xmm0, Assembler::AVX_512bit);
+      } else if (UseAVX == 2) {
         __ vmovdqu(xmm0, Address(from, qword_count, Address::times_8, 32));
         __ vmovdqu(Address(dest, qword_count, Address::times_8, 32), xmm0);
         __ vmovdqu(xmm1, Address(from, qword_count, Address::times_8,  0));
--- a/hotspot/src/cpu/x86/vm/vm_version_x86.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/vm_version_x86.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -35,7 +35,7 @@
 int VM_Version::_cpu;
 int VM_Version::_model;
 int VM_Version::_stepping;
-int VM_Version::_cpuFeatures;
+uint64_t VM_Version::_cpuFeatures;
 const char*           VM_Version::_features_str = "";
 VM_Version::CpuidInfo VM_Version::_cpuid_info   = { 0, };
 
@@ -45,7 +45,7 @@
 address VM_Version::_cpuinfo_cont_addr = 0;
 
 static BufferBlob* stub_blob;
-static const int stub_size = 600;
+static const int stub_size = 1000;
 
 extern "C" {
   typedef void (*get_cpu_info_stub_t)(void*);
@@ -60,15 +60,16 @@
 
   address generate_get_cpu_info() {
     // Flags to test CPU type.
-    const uint32_t HS_EFL_AC           = 0x40000;
-    const uint32_t HS_EFL_ID           = 0x200000;
+    const uint32_t HS_EFL_AC = 0x40000;
+    const uint32_t HS_EFL_ID = 0x200000;
     // Values for when we don't have a CPUID instruction.
     const int      CPU_FAMILY_SHIFT = 8;
-    const uint32_t CPU_FAMILY_386   = (3 << CPU_FAMILY_SHIFT);
-    const uint32_t CPU_FAMILY_486   = (4 << CPU_FAMILY_SHIFT);
+    const uint32_t CPU_FAMILY_386 = (3 << CPU_FAMILY_SHIFT);
+    const uint32_t CPU_FAMILY_486 = (4 << CPU_FAMILY_SHIFT);
 
     Label detect_486, cpu486, detect_586, std_cpuid1, std_cpuid4;
-    Label sef_cpuid, ext_cpuid, ext_cpuid1, ext_cpuid5, ext_cpuid7, done;
+    Label sef_cpuid, ext_cpuid, ext_cpuid1, ext_cpuid5, ext_cpuid7, done, wrapup;
+    Label legacy_setup, save_restore_except, legacy_save_restore, start_simd_check;
 
     StubCodeMark mark(this, "VM_Version", "get_cpu_info_stub");
 #   define __ _masm->
@@ -241,53 +242,6 @@
     __ movl(Address(rsi, 0), rax);
     __ movl(Address(rsi, 4), rdx);
 
-    __ andl(rax, 0x6); // xcr0 bits sse | ymm
-    __ cmpl(rax, 0x6);
-    __ jccb(Assembler::notEqual, sef_cpuid); // jump if AVX is not supported
-
-    //
-    // Some OSs have a bug when upper 128bits of YMM
-    // registers are not restored after a signal processing.
-    // Generate SEGV here (reference through NULL)
-    // and check upper YMM bits after it.
-    //
-    VM_Version::set_avx_cpuFeatures(); // Enable temporary to pass asserts
-    intx saved_useavx = UseAVX;
-    intx saved_usesse = UseSSE;
-    UseAVX = 1;
-    UseSSE = 2;
-
-    // load value into all 32 bytes of ymm7 register
-    __ movl(rcx, VM_Version::ymm_test_value());
-
-    __ movdl(xmm0, rcx);
-    __ pshufd(xmm0, xmm0, 0x00);
-    __ vinsertf128h(xmm0, xmm0, xmm0);
-    __ vmovdqu(xmm7, xmm0);
-#ifdef _LP64
-    __ vmovdqu(xmm8,  xmm0);
-    __ vmovdqu(xmm15, xmm0);
-#endif
-
-    __ xorl(rsi, rsi);
-    VM_Version::set_cpuinfo_segv_addr( __ pc() );
-    // Generate SEGV
-    __ movl(rax, Address(rsi, 0));
-
-    VM_Version::set_cpuinfo_cont_addr( __ pc() );
-    // Returns here after signal. Save xmm0 to check it later.
-    __ lea(rsi, Address(rbp, in_bytes(VM_Version::ymm_save_offset())));
-    __ vmovdqu(Address(rsi,  0), xmm0);
-    __ vmovdqu(Address(rsi, 32), xmm7);
-#ifdef _LP64
-    __ vmovdqu(Address(rsi, 64), xmm8);
-    __ vmovdqu(Address(rsi, 96), xmm15);
-#endif
-
-    VM_Version::clean_cpuFeatures();
-    UseAVX = saved_useavx;
-    UseSSE = saved_usesse;
-
     //
     // cpuid(0x7) Structured Extended Features
     //
@@ -364,9 +318,143 @@
     __ movl(Address(rsi,12), rdx);
 
     //
-    // return
+    // Check if OS has enabled XGETBV instruction to access XCR0
+    // (OSXSAVE feature flag) and CPU supports AVX
+    //
+    __ lea(rsi, Address(rbp, in_bytes(VM_Version::std_cpuid1_offset())));
+    __ movl(rcx, 0x18000000); // cpuid1 bits osxsave | avx
+    __ andl(rcx, Address(rsi, 8)); // cpuid1 bits osxsave | avx
+    __ cmpl(rcx, 0x18000000);
+    __ jccb(Assembler::notEqual, done); // jump if AVX is not supported
+
+    __ movl(rax, 0x6);
+    __ andl(rax, Address(rbp, in_bytes(VM_Version::xem_xcr0_offset()))); // xcr0 bits sse | ymm
+    __ cmpl(rax, 0x6);
+    __ jccb(Assembler::equal, start_simd_check); // return if AVX is not supported
+
+    // we need to bridge farther than imm8, so we use this island as a thunk
+    __ bind(done);
+    __ jmp(wrapup);
+
+    __ bind(start_simd_check);
+    //
+    // Some OSs have a bug when upper 128/256bits of YMM/ZMM
+    // registers are not restored after a signal processing.
+    // Generate SEGV here (reference through NULL)
+    // and check upper YMM/ZMM bits after it.
     //
-    __ bind(done);
+    intx saved_useavx = UseAVX;
+    intx saved_usesse = UseSSE;
+    // check _cpuid_info.sef_cpuid7_ebx.bits.avx512f
+    __ lea(rsi, Address(rbp, in_bytes(VM_Version::sef_cpuid7_offset())));
+    __ movl(rax, 0x10000);
+    __ andl(rax, Address(rsi, 4)); // xcr0 bits sse | ymm
+    __ cmpl(rax, 0x10000);
+    __ jccb(Assembler::notEqual, legacy_setup); // jump if EVEX is not supported
+    // check _cpuid_info.xem_xcr0_eax.bits.opmask
+    // check _cpuid_info.xem_xcr0_eax.bits.zmm512
+    // check _cpuid_info.xem_xcr0_eax.bits.zmm32
+    __ movl(rax, 0xE0);
+    __ andl(rax, Address(rbp, in_bytes(VM_Version::xem_xcr0_offset()))); // xcr0 bits sse | ymm
+    __ cmpl(rax, 0xE0);
+    __ jccb(Assembler::notEqual, legacy_setup); // jump if EVEX is not supported
+
+    // EVEX setup: run in lowest evex mode
+    VM_Version::set_evex_cpuFeatures(); // Enable temporary to pass asserts
+    UseAVX = 3;
+    UseSSE = 2;
+    // load value into all 64 bytes of zmm7 register
+    __ movl(rcx, VM_Version::ymm_test_value());
+    __ movdl(xmm0, rcx);
+    __ movl(rcx, 0xffff);
+#ifdef _LP64
+    __ kmovql(k1, rcx);
+#else
+    __ kmovdl(k1, rcx);
+#endif
+    __ evpbroadcastd(xmm0, xmm0, Assembler::AVX_512bit);
+    __ evmovdqu(xmm7, xmm0, Assembler::AVX_512bit);
+#ifdef _LP64
+    __ evmovdqu(xmm8, xmm0, Assembler::AVX_512bit);
+    __ evmovdqu(xmm31, xmm0, Assembler::AVX_512bit);
+#endif
+    VM_Version::clean_cpuFeatures();
+    __ jmp(save_restore_except);
+
+    __ bind(legacy_setup);
+    // AVX setup
+    VM_Version::set_avx_cpuFeatures(); // Enable temporary to pass asserts
+    UseAVX = 1;
+    UseSSE = 2;
+    // load value into all 32 bytes of ymm7 register
+    __ movl(rcx, VM_Version::ymm_test_value());
+
+    __ movdl(xmm0, rcx);
+    __ pshufd(xmm0, xmm0, 0x00);
+    __ vinsertf128h(xmm0, xmm0, xmm0);
+    __ vmovdqu(xmm7, xmm0);
+#ifdef _LP64
+    __ vmovdqu(xmm8, xmm0);
+    __ vmovdqu(xmm15, xmm0);
+#endif
+    VM_Version::clean_cpuFeatures();
+
+    __ bind(save_restore_except);
+    __ xorl(rsi, rsi);
+    VM_Version::set_cpuinfo_segv_addr(__ pc());
+    // Generate SEGV
+    __ movl(rax, Address(rsi, 0));
+
+    VM_Version::set_cpuinfo_cont_addr(__ pc());
+    // Returns here after signal. Save xmm0 to check it later.
+
+    // check _cpuid_info.sef_cpuid7_ebx.bits.avx512f
+    __ lea(rsi, Address(rbp, in_bytes(VM_Version::sef_cpuid7_offset())));
+    __ movl(rax, 0x10000);
+    __ andl(rax, Address(rsi, 4));
+    __ cmpl(rax, 0x10000);
+    __ jccb(Assembler::notEqual, legacy_save_restore);
+    // check _cpuid_info.xem_xcr0_eax.bits.opmask
+    // check _cpuid_info.xem_xcr0_eax.bits.zmm512
+    // check _cpuid_info.xem_xcr0_eax.bits.zmm32
+    __ movl(rax, 0xE0);
+    __ andl(rax, Address(rbp, in_bytes(VM_Version::xem_xcr0_offset()))); // xcr0 bits sse | ymm
+    __ cmpl(rax, 0xE0);
+    __ jccb(Assembler::notEqual, legacy_save_restore);
+
+    // EVEX check: run in lowest evex mode
+    VM_Version::set_evex_cpuFeatures(); // Enable temporary to pass asserts
+    UseAVX = 3;
+    UseSSE = 2;
+    __ lea(rsi, Address(rbp, in_bytes(VM_Version::zmm_save_offset())));
+    __ evmovdqu(Address(rsi, 0), xmm0, Assembler::AVX_512bit);
+    __ evmovdqu(Address(rsi, 64), xmm7, Assembler::AVX_512bit);
+#ifdef _LP64
+    __ evmovdqu(Address(rsi, 128), xmm8, Assembler::AVX_512bit);
+    __ evmovdqu(Address(rsi, 192), xmm31, Assembler::AVX_512bit);
+#endif
+    VM_Version::clean_cpuFeatures();
+    UseAVX = saved_useavx;
+    UseSSE = saved_usesse;
+    __ jmp(wrapup);
+
+    __ bind(legacy_save_restore);
+    // AVX check
+    VM_Version::set_avx_cpuFeatures(); // Enable temporary to pass asserts
+    UseAVX = 1;
+    UseSSE = 2;
+    __ lea(rsi, Address(rbp, in_bytes(VM_Version::ymm_save_offset())));
+    __ vmovdqu(Address(rsi, 0), xmm0);
+    __ vmovdqu(Address(rsi, 32), xmm7);
+#ifdef _LP64
+    __ vmovdqu(Address(rsi, 64), xmm8);
+    __ vmovdqu(Address(rsi, 96), xmm15);
+#endif
+    VM_Version::clean_cpuFeatures();
+    UseAVX = saved_useavx;
+    UseSSE = saved_usesse;
+
+    __ bind(wrapup);
     __ popf();
     __ pop(rsi);
     __ pop(rbx);
@@ -459,6 +547,29 @@
   if (UseSSE < 1)
     _cpuFeatures &= ~CPU_SSE;
 
+  // first try initial setting and detect what we can support
+  if (UseAVX > 0) {
+    if (UseAVX > 2 && supports_evex()) {
+      UseAVX = 3;
+    } else if (UseAVX > 1 && supports_avx2()) {
+      UseAVX = 2;
+    } else if (UseAVX > 0 && supports_avx()) {
+      UseAVX = 1;
+    } else {
+      UseAVX = 0;
+    }
+  } else if (UseAVX < 0) {
+    UseAVX = 0;
+  }
+
+  if (UseAVX < 3) {
+    _cpuFeatures &= ~CPU_AVX512F;
+    _cpuFeatures &= ~CPU_AVX512DQ;
+    _cpuFeatures &= ~CPU_AVX512CD;
+    _cpuFeatures &= ~CPU_AVX512BW;
+    _cpuFeatures &= ~CPU_AVX512VL;
+  }
+
   if (UseAVX < 2)
     _cpuFeatures &= ~CPU_AVX2;
 
@@ -474,7 +585,7 @@
   }
 
   char buf[256];
-  jio_snprintf(buf, sizeof(buf), "(%u cores per cpu, %u threads per core) family %d model %d stepping %d%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s",
+  jio_snprintf(buf, sizeof(buf), "(%u cores per cpu, %u threads per core) family %d model %d stepping %d%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s",
                cores_per_cpu(), threads_per_core(),
                cpu_family(), _model, _stepping,
                (supports_cmov() ? ", cmov" : ""),
@@ -504,7 +615,8 @@
                (supports_tscinv() ? ", tscinv": ""),
                (supports_bmi1() ? ", bmi1" : ""),
                (supports_bmi2() ? ", bmi2" : ""),
-               (supports_adx() ? ", adx" : ""));
+               (supports_adx() ? ", adx" : ""),
+               (supports_evex() ? ", evex" : ""));
   _features_str = os::strdup(buf);
 
   // UseSSE is set to the smaller of what hardware supports and what
@@ -521,13 +633,6 @@
   if (!supports_sse ()) // Drop to 0 if no SSE  support
     UseSSE = 0;
 
-  if (UseAVX > 2) UseAVX=2;
-  if (UseAVX < 0) UseAVX=0;
-  if (!supports_avx2()) // Drop to 1 if no AVX2 support
-    UseAVX = MIN2((intx)1,UseAVX);
-  if (!supports_avx ()) // Drop to 0 if no AVX  support
-    UseAVX = 0;
-
   // Use AES instructions if available.
   if (supports_aes()) {
     if (FLAG_IS_DEFAULT(UseAES)) {
@@ -598,7 +703,8 @@
       if ((_model == CPU_MODEL_HASWELL_E3) ||
           (_model == CPU_MODEL_HASWELL_E7 && _stepping < 3) ||
           (_model == CPU_MODEL_BROADWELL  && _stepping < 4)) {
-        if (!UnlockExperimentalVMOptions) {
+        // currently a collision between SKL and HSW_E3
+        if (!UnlockExperimentalVMOptions && UseAVX < 3) {
           vm_exit_during_initialization("UseRTMLocking is only available as experimental option on this platform. It must be enabled via -XX:+UnlockExperimentalVMOptions flag.");
         } else {
           warning("UseRTMLocking is only available as experimental option on this platform.");
@@ -651,10 +757,10 @@
   if (MaxVectorSize > 0) {
     if (!is_power_of_2(MaxVectorSize)) {
       warning("MaxVectorSize must be a power of 2");
-      FLAG_SET_DEFAULT(MaxVectorSize, 32);
+      FLAG_SET_DEFAULT(MaxVectorSize, 64);
     }
-    if (MaxVectorSize > 32) {
-      FLAG_SET_DEFAULT(MaxVectorSize, 32);
+    if (MaxVectorSize > 64) {
+      FLAG_SET_DEFAULT(MaxVectorSize, 64);
     }
     if (MaxVectorSize > 16 && (UseAVX == 0 || !os_supports_avx_vectors())) {
       // 32 bytes vectors (in YMM) are only supported with AVX+
--- a/hotspot/src/cpu/x86/vm/vm_version_x86.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/vm_version_x86.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -208,20 +208,33 @@
                    bmi2 : 1,
                    erms : 1,
                         : 1,
-                   rtm  : 1,
-                        : 7,
-                   adx  : 1,
-                        : 12;
+                    rtm : 1,
+                        : 4,
+                avx512f : 1,
+               avx512dq : 1,
+                        : 1,
+                    adx : 1,
+                        : 6,
+               avx512pf : 1,
+               avx512er : 1,
+               avx512cd : 1,
+                        : 1,
+               avx512bw : 1,
+               avx512vl : 1;
     } bits;
   };
 
   union XemXcr0Eax {
     uint32_t value;
     struct {
-      uint32_t x87 : 1,
-               sse : 1,
-               ymm : 1,
-                   : 29;
+      uint32_t x87    : 1,
+               sse    : 1,
+               ymm    : 1,
+                      : 2,
+               opmask : 1,
+               zmm512 : 1,
+                zmm32 : 1,
+                      : 24;
     } bits;
   };
 
@@ -229,43 +242,51 @@
   static int _cpu;
   static int _model;
   static int _stepping;
-  static int _cpuFeatures;     // features returned by the "cpuid" instruction
-                               // 0 if this instruction is not available
+  static uint64_t _cpuFeatures; // features returned by the "cpuid" instruction
+                                // 0 if this instruction is not available
   static const char* _features_str;
 
   static address   _cpuinfo_segv_addr; // address of instruction which causes SEGV
   static address   _cpuinfo_cont_addr; // address of instruction after the one which causes SEGV
 
   enum {
-    CPU_CX8    = (1 << 0), // next bits are from cpuid 1 (EDX)
-    CPU_CMOV   = (1 << 1),
-    CPU_FXSR   = (1 << 2),
-    CPU_HT     = (1 << 3),
-    CPU_MMX    = (1 << 4),
-    CPU_3DNOW_PREFETCH  = (1 << 5), // Processor supports 3dnow prefetch and prefetchw instructions
-                                    // may not necessarily support other 3dnow instructions
-    CPU_SSE    = (1 << 6),
-    CPU_SSE2   = (1 << 7),
-    CPU_SSE3   = (1 << 8), // SSE3 comes from cpuid 1 (ECX)
-    CPU_SSSE3  = (1 << 9),
-    CPU_SSE4A  = (1 << 10),
-    CPU_SSE4_1 = (1 << 11),
-    CPU_SSE4_2 = (1 << 12),
-    CPU_POPCNT = (1 << 13),
-    CPU_LZCNT  = (1 << 14),
-    CPU_TSC    = (1 << 15),
-    CPU_TSCINV = (1 << 16),
-    CPU_AVX    = (1 << 17),
-    CPU_AVX2   = (1 << 18),
-    CPU_AES    = (1 << 19),
-    CPU_ERMS   = (1 << 20), // enhanced 'rep movsb/stosb' instructions
-    CPU_CLMUL  = (1 << 21), // carryless multiply for CRC
-    CPU_BMI1   = (1 << 22),
-    CPU_BMI2   = (1 << 23),
-    CPU_RTM    = (1 << 24),  // Restricted Transactional Memory instructions
-    CPU_ADX    = (1 << 25)
+    CPU_CX8      = (1 << 0), // next bits are from cpuid 1 (EDX)
+    CPU_CMOV     = (1 << 1),
+    CPU_FXSR     = (1 << 2),
+    CPU_HT       = (1 << 3),
+    CPU_MMX      = (1 << 4),
+    CPU_3DNOW_PREFETCH = (1 << 5), // Processor supports 3dnow prefetch and prefetchw instructions
+                                   // may not necessarily support other 3dnow instructions
+    CPU_SSE      = (1 << 6),
+    CPU_SSE2     = (1 << 7),
+    CPU_SSE3     = (1 << 8),  // SSE3 comes from cpuid 1 (ECX)
+    CPU_SSSE3    = (1 << 9),
+    CPU_SSE4A    = (1 << 10),
+    CPU_SSE4_1   = (1 << 11),
+    CPU_SSE4_2   = (1 << 12),
+    CPU_POPCNT   = (1 << 13),
+    CPU_LZCNT    = (1 << 14),
+    CPU_TSC      = (1 << 15),
+    CPU_TSCINV   = (1 << 16),
+    CPU_AVX      = (1 << 17),
+    CPU_AVX2     = (1 << 18),
+    CPU_AES      = (1 << 19),
+    CPU_ERMS     = (1 << 20), // enhanced 'rep movsb/stosb' instructions
+    CPU_CLMUL    = (1 << 21), // carryless multiply for CRC
+    CPU_BMI1     = (1 << 22),
+    CPU_BMI2     = (1 << 23),
+    CPU_RTM      = (1 << 24), // Restricted Transactional Memory instructions
+    CPU_ADX      = (1 << 25),
+    CPU_AVX512F  = (1 << 26), // AVX 512bit foundation instructions
+    CPU_AVX512DQ = (1 << 27),
+    CPU_AVX512PF = (1 << 28),
+    CPU_AVX512ER = (1 << 29),
+    CPU_AVX512CD = (1 << 30),
+    CPU_AVX512BW = (1 << 31)
   } cpuFeatureFlags;
 
+#define CPU_AVX512VL 0x100000000 // EVEX instructions with smaller vector length : enums are limited to 32bit
+
   enum {
     // AMD
     CPU_FAMILY_AMD_11H       = 0x11,
@@ -282,7 +303,8 @@
     CPU_MODEL_IVYBRIDGE_EP   = 0x3a,
     CPU_MODEL_HASWELL_E3     = 0x3c,
     CPU_MODEL_HASWELL_E7     = 0x3f,
-    CPU_MODEL_BROADWELL      = 0x3d
+    CPU_MODEL_BROADWELL      = 0x3d,
+    CPU_MODEL_SKYLAKE        = CPU_MODEL_HASWELL_E3
   } cpuExtendedFamily;
 
   // cpuid information block.  All info derived from executing cpuid with
@@ -376,6 +398,9 @@
 
     // Space to save ymm registers after signal handle
     int          ymm_save[8*4]; // Save ymm0, ymm7, ymm8, ymm15
+
+    // Space to save zmm registers after signal handle
+    int          zmm_save[16*4]; // Save zmm0, zmm7, zmm8, zmm31
   };
 
   // The actual cpuid info block
@@ -404,8 +429,8 @@
     return result;
   }
 
-  static uint32_t feature_flags() {
-    uint32_t result = 0;
+  static uint64_t feature_flags() {
+    uint64_t result = 0;
     if (_cpuid_info.std_cpuid1_edx.bits.cmpxchg8 != 0)
       result |= CPU_CX8;
     if (_cpuid_info.std_cpuid1_edx.bits.cmov != 0)
@@ -440,6 +465,24 @@
       result |= CPU_AVX;
       if (_cpuid_info.sef_cpuid7_ebx.bits.avx2 != 0)
         result |= CPU_AVX2;
+      if (_cpuid_info.sef_cpuid7_ebx.bits.avx512f != 0 &&
+          _cpuid_info.xem_xcr0_eax.bits.opmask != 0 &&
+          _cpuid_info.xem_xcr0_eax.bits.zmm512 != 0 &&
+          _cpuid_info.xem_xcr0_eax.bits.zmm32 != 0) {
+        result |= CPU_AVX512F;
+        if (_cpuid_info.sef_cpuid7_ebx.bits.avx512cd != 0)
+          result |= CPU_AVX512CD;
+        if (_cpuid_info.sef_cpuid7_ebx.bits.avx512dq != 0)
+          result |= CPU_AVX512DQ;
+        if (_cpuid_info.sef_cpuid7_ebx.bits.avx512pf != 0)
+          result |= CPU_AVX512PF;
+        if (_cpuid_info.sef_cpuid7_ebx.bits.avx512er != 0)
+          result |= CPU_AVX512ER;
+        if (_cpuid_info.sef_cpuid7_ebx.bits.avx512bw != 0)
+          result |= CPU_AVX512BW;
+        if (_cpuid_info.sef_cpuid7_ebx.bits.avx512vl != 0)
+          result |= CPU_AVX512VL;
+      }
     }
     if(_cpuid_info.sef_cpuid7_ebx.bits.bmi1 != 0)
       result |= CPU_BMI1;
@@ -484,18 +527,31 @@
   }
 
   static bool os_supports_avx_vectors() {
-    if (!supports_avx()) {
-      return false;
-    }
-    // Verify that OS save/restore all bits of AVX registers
-    // during signal processing.
-    int nreg = 2 LP64_ONLY(+2);
-    for (int i = 0; i < 8 * nreg; i++) { // 32 bytes per ymm register
-      if (_cpuid_info.ymm_save[i] != ymm_test_value()) {
-        return false;
+    bool retVal = false;
+    if (supports_evex()) {
+      // Verify that OS save/restore all bits of EVEX registers
+      // during signal processing.
+      int nreg = 2 LP64_ONLY(+2);
+      retVal = true;
+      for (int i = 0; i < 16 * nreg; i++) { // 64 bytes per zmm register
+        if (_cpuid_info.zmm_save[i] != ymm_test_value()) {
+          retVal = false;
+          break;
+        }
+      }
+    } else if (supports_avx()) {
+      // Verify that OS save/restore all bits of AVX registers
+      // during signal processing.
+      int nreg = 2 LP64_ONLY(+2);
+      retVal = true;
+      for (int i = 0; i < 8 * nreg; i++) { // 32 bytes per ymm register
+        if (_cpuid_info.ymm_save[i] != ymm_test_value()) {
+          retVal = false;
+          break;
+        }
       }
     }
-    return true;
+    return retVal;
   }
 
   static void get_processor_features();
@@ -515,6 +571,7 @@
   static ByteSize tpl_cpuidB2_offset() { return byte_offset_of(CpuidInfo, tpl_cpuidB2_eax); }
   static ByteSize xem_xcr0_offset() { return byte_offset_of(CpuidInfo, xem_xcr0_eax); }
   static ByteSize ymm_save_offset() { return byte_offset_of(CpuidInfo, ymm_save); }
+  static ByteSize zmm_save_offset() { return byte_offset_of(CpuidInfo, zmm_save); }
 
   // The value used to check ymm register after signal handle
   static int ymm_test_value()    { return 0xCAFEBABE; }
@@ -527,6 +584,7 @@
 
   static void clean_cpuFeatures()   { _cpuFeatures = 0; }
   static void set_avx_cpuFeatures() { _cpuFeatures = (CPU_SSE | CPU_SSE2 | CPU_AVX); }
+  static void set_evex_cpuFeatures() { _cpuFeatures = (CPU_AVX512F | CPU_SSE | CPU_SSE2 ); }
 
 
   // Initialization
@@ -636,7 +694,14 @@
   static bool supports_rtm()      { return (_cpuFeatures & CPU_RTM) != 0; }
   static bool supports_bmi1()     { return (_cpuFeatures & CPU_BMI1) != 0; }
   static bool supports_bmi2()     { return (_cpuFeatures & CPU_BMI2) != 0; }
-  static bool supports_adx()     { return (_cpuFeatures & CPU_ADX) != 0; }
+  static bool supports_adx()      { return (_cpuFeatures & CPU_ADX) != 0; }
+  static bool supports_evex()     { return (_cpuFeatures & CPU_AVX512F) != 0; }
+  static bool supports_avx512dq() { return (_cpuFeatures & CPU_AVX512DQ) != 0; }
+  static bool supports_avx512pf() { return (_cpuFeatures & CPU_AVX512PF) != 0; }
+  static bool supports_avx512er() { return (_cpuFeatures & CPU_AVX512ER) != 0; }
+  static bool supports_avx512cd() { return (_cpuFeatures & CPU_AVX512CD) != 0; }
+  static bool supports_avx512bw() { return (_cpuFeatures & CPU_AVX512BW) != 0; }
+  static bool supports_avx512vl() { return (_cpuFeatures & CPU_AVX512VL) != 0; }
   // Intel features
   static bool is_intel_family_core() { return is_intel() &&
                                        extended_cpu_family() == CPU_FAMILY_INTEL_CORE; }
--- a/hotspot/src/cpu/x86/vm/vmreg_x86.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/vmreg_x86.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -47,13 +47,22 @@
   }
 
   XMMRegister xreg = ::as_XMMRegister(0);
-  for ( ; i < ConcreteRegisterImpl::max_xmm ; ) {
-    for (int j = 0 ; j < 8 ; j++) {
+  for (; i < ConcreteRegisterImpl::max_xmm;) {
+    for (int j = 0 ; j < XMMRegisterImpl::max_slots_per_register ; j++) {
       regName[i++] = xreg->name();
     }
     xreg = xreg->successor();
   }
+
+  KRegister kreg = ::as_KRegister(0);
+  for (; i < ConcreteRegisterImpl::max_kpr;) {
+    for (int j = 0; j < KRegisterImpl::max_slots_per_register; j++) {
+      regName[i++] = kreg->name();
+    }
+    kreg = kreg->successor();
+  }
+
   for ( ; i < ConcreteRegisterImpl::number_of_registers ; i ++ ) {
-    regName[i] = "NON-GPR-FPR-XMM";
+    regName[i] = "NON-GPR-FPR-XMM-KREG";
   }
 }
--- a/hotspot/src/cpu/x86/vm/vmreg_x86.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/vmreg_x86.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -36,7 +36,24 @@
 }
 
 inline bool is_XMMRegister() {
-  return value() >= ConcreteRegisterImpl::max_fpr && value() < ConcreteRegisterImpl::max_xmm;
+  int uarch_max_xmm = ConcreteRegisterImpl::max_xmm;
+
+#ifdef _LP64
+  if (UseAVX < 3) {
+    int half_xmm = (XMMRegisterImpl::max_slots_per_register * XMMRegisterImpl::number_of_registers) / 2;
+    uarch_max_xmm -= half_xmm;
+  }
+#endif
+
+  return (value() >= ConcreteRegisterImpl::max_fpr && value() < uarch_max_xmm);
+}
+
+inline bool is_KRegister() {
+  if (UseAVX > 2) {
+    return value() >= ConcreteRegisterImpl::max_xmm && value() < ConcreteRegisterImpl::max_kpr;
+  } else {
+    return false;
+  }
 }
 
 inline Register as_Register() {
@@ -59,7 +76,13 @@
 inline XMMRegister as_XMMRegister() {
   assert( is_XMMRegister() && is_even(value()), "must be" );
   // Yuk
-  return ::as_XMMRegister((value() - ConcreteRegisterImpl::max_fpr) >> 3);
+  return ::as_XMMRegister((value() - ConcreteRegisterImpl::max_fpr) >> 4);
+}
+
+inline KRegister as_KRegister() {
+  assert(is_KRegister(), "must be");
+  // Yuk
+  return ::as_KRegister((value() - ConcreteRegisterImpl::max_xmm));
 }
 
 inline   bool is_concrete() {
--- a/hotspot/src/cpu/x86/vm/vmreg_x86.inline.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/vmreg_x86.inline.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -39,7 +39,11 @@
 }
 
 inline VMReg XMMRegisterImpl::as_VMReg() {
-  return VMRegImpl::as_VMReg((encoding() << 3) + ConcreteRegisterImpl::max_fpr);
+  return VMRegImpl::as_VMReg((encoding() << 4) + ConcreteRegisterImpl::max_fpr);
+}
+
+inline VMReg KRegisterImpl::as_VMReg() {
+  return VMRegImpl::as_VMReg(encoding() + ConcreteRegisterImpl::max_xmm);
 }
 
 #endif // CPU_X86_VM_VMREG_X86_INLINE_HPP
--- a/hotspot/src/cpu/x86/vm/x86.ad	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/x86.ad	Wed Jul 05 20:35:10 2017 +0200
@@ -59,15 +59,19 @@
 //
 // The encoding number is the actual bit-pattern placed into the opcodes.
 
-// XMM registers.  256-bit registers or 8 words each, labeled (a)-h.
+// XMM registers.  512-bit registers or 8 words each, labeled (a)-p.
 // Word a in each register holds a Float, words ab hold a Double.
 // The whole registers are used in SSE4.2 version intrinsics,
 // array copy stubs and superword operations (see UseSSE42Intrinsics,
 // UseXMMForArrayCopy and UseSuperword flags).
-// XMM8-XMM15 must be encoded with REX (VEX for UseAVX).
+// For pre EVEX enabled architectures:
+//      XMM8-XMM15 must be encoded with REX (VEX for UseAVX)
+// For EVEX enabled architectures:
+//      XMM8-XMM31 must be encoded with REX (EVEX for UseAVX).
+//
 // Linux ABI:   No register preserved across function calls
 //              XMM0-XMM7 might hold parameters
-// Windows ABI: XMM6-XMM15 preserved across function calls
+// Windows ABI: XMM6-XMM31 preserved across function calls
 //              XMM0-XMM3 might hold parameters
 
 reg_def XMM0 ( SOC, SOC, Op_RegF, 0, xmm0->as_VMReg());
@@ -78,6 +82,14 @@
 reg_def XMM0f( SOC, SOC, Op_RegF, 0, xmm0->as_VMReg()->next(5));
 reg_def XMM0g( SOC, SOC, Op_RegF, 0, xmm0->as_VMReg()->next(6));
 reg_def XMM0h( SOC, SOC, Op_RegF, 0, xmm0->as_VMReg()->next(7));
+reg_def XMM0i( SOC, SOC, Op_RegF, 0, xmm0->as_VMReg()->next(8));
+reg_def XMM0j( SOC, SOC, Op_RegF, 0, xmm0->as_VMReg()->next(9));
+reg_def XMM0k( SOC, SOC, Op_RegF, 0, xmm0->as_VMReg()->next(10));
+reg_def XMM0l( SOC, SOC, Op_RegF, 0, xmm0->as_VMReg()->next(11));
+reg_def XMM0m( SOC, SOC, Op_RegF, 0, xmm0->as_VMReg()->next(12));
+reg_def XMM0n( SOC, SOC, Op_RegF, 0, xmm0->as_VMReg()->next(13));
+reg_def XMM0o( SOC, SOC, Op_RegF, 0, xmm0->as_VMReg()->next(14));
+reg_def XMM0p( SOC, SOC, Op_RegF, 0, xmm0->as_VMReg()->next(15));
 
 reg_def XMM1 ( SOC, SOC, Op_RegF, 1, xmm1->as_VMReg());
 reg_def XMM1b( SOC, SOC, Op_RegF, 1, xmm1->as_VMReg()->next(1));
@@ -87,6 +99,14 @@
 reg_def XMM1f( SOC, SOC, Op_RegF, 1, xmm1->as_VMReg()->next(5));
 reg_def XMM1g( SOC, SOC, Op_RegF, 1, xmm1->as_VMReg()->next(6));
 reg_def XMM1h( SOC, SOC, Op_RegF, 1, xmm1->as_VMReg()->next(7));
+reg_def XMM1i( SOC, SOC, Op_RegF, 1, xmm1->as_VMReg()->next(8));
+reg_def XMM1j( SOC, SOC, Op_RegF, 1, xmm1->as_VMReg()->next(9));
+reg_def XMM1k( SOC, SOC, Op_RegF, 1, xmm1->as_VMReg()->next(10));
+reg_def XMM1l( SOC, SOC, Op_RegF, 1, xmm1->as_VMReg()->next(11));
+reg_def XMM1m( SOC, SOC, Op_RegF, 1, xmm1->as_VMReg()->next(12));
+reg_def XMM1n( SOC, SOC, Op_RegF, 1, xmm1->as_VMReg()->next(13));
+reg_def XMM1o( SOC, SOC, Op_RegF, 1, xmm1->as_VMReg()->next(14));
+reg_def XMM1p( SOC, SOC, Op_RegF, 1, xmm1->as_VMReg()->next(15));
 
 reg_def XMM2 ( SOC, SOC, Op_RegF, 2, xmm2->as_VMReg());
 reg_def XMM2b( SOC, SOC, Op_RegF, 2, xmm2->as_VMReg()->next(1));
@@ -96,6 +116,14 @@
 reg_def XMM2f( SOC, SOC, Op_RegF, 2, xmm2->as_VMReg()->next(5));
 reg_def XMM2g( SOC, SOC, Op_RegF, 2, xmm2->as_VMReg()->next(6));
 reg_def XMM2h( SOC, SOC, Op_RegF, 2, xmm2->as_VMReg()->next(7));
+reg_def XMM2i( SOC, SOC, Op_RegF, 2, xmm2->as_VMReg()->next(8));
+reg_def XMM2j( SOC, SOC, Op_RegF, 2, xmm2->as_VMReg()->next(9));
+reg_def XMM2k( SOC, SOC, Op_RegF, 2, xmm2->as_VMReg()->next(10));
+reg_def XMM2l( SOC, SOC, Op_RegF, 2, xmm2->as_VMReg()->next(11));
+reg_def XMM2m( SOC, SOC, Op_RegF, 2, xmm2->as_VMReg()->next(12));
+reg_def XMM2n( SOC, SOC, Op_RegF, 2, xmm2->as_VMReg()->next(13));
+reg_def XMM2o( SOC, SOC, Op_RegF, 2, xmm2->as_VMReg()->next(14));
+reg_def XMM2p( SOC, SOC, Op_RegF, 2, xmm2->as_VMReg()->next(15));
 
 reg_def XMM3 ( SOC, SOC, Op_RegF, 3, xmm3->as_VMReg());
 reg_def XMM3b( SOC, SOC, Op_RegF, 3, xmm3->as_VMReg()->next(1));
@@ -105,6 +133,14 @@
 reg_def XMM3f( SOC, SOC, Op_RegF, 3, xmm3->as_VMReg()->next(5));
 reg_def XMM3g( SOC, SOC, Op_RegF, 3, xmm3->as_VMReg()->next(6));
 reg_def XMM3h( SOC, SOC, Op_RegF, 3, xmm3->as_VMReg()->next(7));
+reg_def XMM3i( SOC, SOC, Op_RegF, 3, xmm3->as_VMReg()->next(8));
+reg_def XMM3j( SOC, SOC, Op_RegF, 3, xmm3->as_VMReg()->next(9));
+reg_def XMM3k( SOC, SOC, Op_RegF, 3, xmm3->as_VMReg()->next(10));
+reg_def XMM3l( SOC, SOC, Op_RegF, 3, xmm3->as_VMReg()->next(11));
+reg_def XMM3m( SOC, SOC, Op_RegF, 3, xmm3->as_VMReg()->next(12));
+reg_def XMM3n( SOC, SOC, Op_RegF, 3, xmm3->as_VMReg()->next(13));
+reg_def XMM3o( SOC, SOC, Op_RegF, 3, xmm3->as_VMReg()->next(14));
+reg_def XMM3p( SOC, SOC, Op_RegF, 3, xmm3->as_VMReg()->next(15));
 
 reg_def XMM4 ( SOC, SOC, Op_RegF, 4, xmm4->as_VMReg());
 reg_def XMM4b( SOC, SOC, Op_RegF, 4, xmm4->as_VMReg()->next(1));
@@ -114,6 +150,14 @@
 reg_def XMM4f( SOC, SOC, Op_RegF, 4, xmm4->as_VMReg()->next(5));
 reg_def XMM4g( SOC, SOC, Op_RegF, 4, xmm4->as_VMReg()->next(6));
 reg_def XMM4h( SOC, SOC, Op_RegF, 4, xmm4->as_VMReg()->next(7));
+reg_def XMM4i( SOC, SOC, Op_RegF, 4, xmm4->as_VMReg()->next(8));
+reg_def XMM4j( SOC, SOC, Op_RegF, 4, xmm4->as_VMReg()->next(9));
+reg_def XMM4k( SOC, SOC, Op_RegF, 4, xmm4->as_VMReg()->next(10));
+reg_def XMM4l( SOC, SOC, Op_RegF, 4, xmm4->as_VMReg()->next(11));
+reg_def XMM4m( SOC, SOC, Op_RegF, 4, xmm4->as_VMReg()->next(12));
+reg_def XMM4n( SOC, SOC, Op_RegF, 4, xmm4->as_VMReg()->next(13));
+reg_def XMM4o( SOC, SOC, Op_RegF, 4, xmm4->as_VMReg()->next(14));
+reg_def XMM4p( SOC, SOC, Op_RegF, 4, xmm4->as_VMReg()->next(15));
 
 reg_def XMM5 ( SOC, SOC, Op_RegF, 5, xmm5->as_VMReg());
 reg_def XMM5b( SOC, SOC, Op_RegF, 5, xmm5->as_VMReg()->next(1));
@@ -123,6 +167,14 @@
 reg_def XMM5f( SOC, SOC, Op_RegF, 5, xmm5->as_VMReg()->next(5));
 reg_def XMM5g( SOC, SOC, Op_RegF, 5, xmm5->as_VMReg()->next(6));
 reg_def XMM5h( SOC, SOC, Op_RegF, 5, xmm5->as_VMReg()->next(7));
+reg_def XMM5i( SOC, SOC, Op_RegF, 5, xmm5->as_VMReg()->next(8));
+reg_def XMM5j( SOC, SOC, Op_RegF, 5, xmm5->as_VMReg()->next(9));
+reg_def XMM5k( SOC, SOC, Op_RegF, 5, xmm5->as_VMReg()->next(10));
+reg_def XMM5l( SOC, SOC, Op_RegF, 5, xmm5->as_VMReg()->next(11));
+reg_def XMM5m( SOC, SOC, Op_RegF, 5, xmm5->as_VMReg()->next(12));
+reg_def XMM5n( SOC, SOC, Op_RegF, 5, xmm5->as_VMReg()->next(13));
+reg_def XMM5o( SOC, SOC, Op_RegF, 5, xmm5->as_VMReg()->next(14));
+reg_def XMM5p( SOC, SOC, Op_RegF, 5, xmm5->as_VMReg()->next(15));
 
 #ifdef _WIN64
 
@@ -134,6 +186,14 @@
 reg_def XMM6f( SOC, SOE, Op_RegF, 6, xmm6->as_VMReg()->next(5));
 reg_def XMM6g( SOC, SOE, Op_RegF, 6, xmm6->as_VMReg()->next(6));
 reg_def XMM6h( SOC, SOE, Op_RegF, 6, xmm6->as_VMReg()->next(7));
+reg_def XMM6i( SOC, SOE, Op_RegF, 6, xmm6->as_VMReg()->next(8));
+reg_def XMM6j( SOC, SOE, Op_RegF, 6, xmm6->as_VMReg()->next(9));
+reg_def XMM6k( SOC, SOE, Op_RegF, 6, xmm6->as_VMReg()->next(10));
+reg_def XMM6l( SOC, SOE, Op_RegF, 6, xmm6->as_VMReg()->next(11));
+reg_def XMM6m( SOC, SOE, Op_RegF, 6, xmm6->as_VMReg()->next(12));
+reg_def XMM6n( SOC, SOE, Op_RegF, 6, xmm6->as_VMReg()->next(13));
+reg_def XMM6o( SOC, SOE, Op_RegF, 6, xmm6->as_VMReg()->next(14));
+reg_def XMM6p( SOC, SOE, Op_RegF, 6, xmm6->as_VMReg()->next(15));
 
 reg_def XMM7 ( SOC, SOE, Op_RegF, 7, xmm7->as_VMReg());
 reg_def XMM7b( SOC, SOE, Op_RegF, 7, xmm7->as_VMReg()->next(1));
@@ -143,6 +203,14 @@
 reg_def XMM7f( SOC, SOE, Op_RegF, 7, xmm7->as_VMReg()->next(5));
 reg_def XMM7g( SOC, SOE, Op_RegF, 7, xmm7->as_VMReg()->next(6));
 reg_def XMM7h( SOC, SOE, Op_RegF, 7, xmm7->as_VMReg()->next(7));
+reg_def XMM7i( SOC, SOE, Op_RegF, 7, xmm7->as_VMReg()->next(8));
+reg_def XMM7j( SOC, SOE, Op_RegF, 7, xmm7->as_VMReg()->next(9));
+reg_def XMM7k( SOC, SOE, Op_RegF, 7, xmm7->as_VMReg()->next(10));
+reg_def XMM7l( SOC, SOE, Op_RegF, 7, xmm7->as_VMReg()->next(11));
+reg_def XMM7m( SOC, SOE, Op_RegF, 7, xmm7->as_VMReg()->next(12));
+reg_def XMM7n( SOC, SOE, Op_RegF, 7, xmm7->as_VMReg()->next(13));
+reg_def XMM7o( SOC, SOE, Op_RegF, 7, xmm7->as_VMReg()->next(14));
+reg_def XMM7p( SOC, SOE, Op_RegF, 7, xmm7->as_VMReg()->next(15));
 
 reg_def XMM8 ( SOC, SOE, Op_RegF, 8, xmm8->as_VMReg());
 reg_def XMM8b( SOC, SOE, Op_RegF, 8, xmm8->as_VMReg()->next(1));
@@ -152,6 +220,14 @@
 reg_def XMM8f( SOC, SOE, Op_RegF, 8, xmm8->as_VMReg()->next(5));
 reg_def XMM8g( SOC, SOE, Op_RegF, 8, xmm8->as_VMReg()->next(6));
 reg_def XMM8h( SOC, SOE, Op_RegF, 8, xmm8->as_VMReg()->next(7));
+reg_def XMM8i( SOC, SOE, Op_RegF, 8, xmm8->as_VMReg()->next(8));
+reg_def XMM8j( SOC, SOE, Op_RegF, 8, xmm8->as_VMReg()->next(9));
+reg_def XMM8k( SOC, SOE, Op_RegF, 8, xmm8->as_VMReg()->next(10));
+reg_def XMM8l( SOC, SOE, Op_RegF, 8, xmm8->as_VMReg()->next(11));
+reg_def XMM8m( SOC, SOE, Op_RegF, 8, xmm8->as_VMReg()->next(12));
+reg_def XMM8n( SOC, SOE, Op_RegF, 8, xmm8->as_VMReg()->next(13));
+reg_def XMM8o( SOC, SOE, Op_RegF, 8, xmm8->as_VMReg()->next(14));
+reg_def XMM8p( SOC, SOE, Op_RegF, 8, xmm8->as_VMReg()->next(15));
 
 reg_def XMM9 ( SOC, SOE, Op_RegF, 9, xmm9->as_VMReg());
 reg_def XMM9b( SOC, SOE, Op_RegF, 9, xmm9->as_VMReg()->next(1));
@@ -161,6 +237,14 @@
 reg_def XMM9f( SOC, SOE, Op_RegF, 9, xmm9->as_VMReg()->next(5));
 reg_def XMM9g( SOC, SOE, Op_RegF, 9, xmm9->as_VMReg()->next(6));
 reg_def XMM9h( SOC, SOE, Op_RegF, 9, xmm9->as_VMReg()->next(7));
+reg_def XMM9i( SOC, SOE, Op_RegF, 9, xmm9->as_VMReg()->next(8));
+reg_def XMM9j( SOC, SOE, Op_RegF, 9, xmm9->as_VMReg()->next(9));
+reg_def XMM9k( SOC, SOE, Op_RegF, 9, xmm9->as_VMReg()->next(10));
+reg_def XMM9l( SOC, SOE, Op_RegF, 9, xmm9->as_VMReg()->next(11));
+reg_def XMM9m( SOC, SOE, Op_RegF, 9, xmm9->as_VMReg()->next(12));
+reg_def XMM9n( SOC, SOE, Op_RegF, 9, xmm9->as_VMReg()->next(13));
+reg_def XMM9o( SOC, SOE, Op_RegF, 9, xmm9->as_VMReg()->next(14));
+reg_def XMM9p( SOC, SOE, Op_RegF, 9, xmm9->as_VMReg()->next(15));
 
 reg_def XMM10 ( SOC, SOE, Op_RegF, 10, xmm10->as_VMReg());
 reg_def XMM10b( SOC, SOE, Op_RegF, 10, xmm10->as_VMReg()->next(1));
@@ -170,6 +254,14 @@
 reg_def XMM10f( SOC, SOE, Op_RegF, 10, xmm10->as_VMReg()->next(5));
 reg_def XMM10g( SOC, SOE, Op_RegF, 10, xmm10->as_VMReg()->next(6));
 reg_def XMM10h( SOC, SOE, Op_RegF, 10, xmm10->as_VMReg()->next(7));
+reg_def XMM10i( SOC, SOE, Op_RegF, 10, xmm10->as_VMReg()->next(8));
+reg_def XMM10j( SOC, SOE, Op_RegF, 10, xmm10->as_VMReg()->next(9));
+reg_def XMM10k( SOC, SOE, Op_RegF, 10, xmm10->as_VMReg()->next(10));
+reg_def XMM10l( SOC, SOE, Op_RegF, 10, xmm10->as_VMReg()->next(11));
+reg_def XMM10m( SOC, SOE, Op_RegF, 10, xmm10->as_VMReg()->next(12));
+reg_def XMM10n( SOC, SOE, Op_RegF, 10, xmm10->as_VMReg()->next(13));
+reg_def XMM10o( SOC, SOE, Op_RegF, 10, xmm10->as_VMReg()->next(14));
+reg_def XMM10p( SOC, SOE, Op_RegF, 10, xmm10->as_VMReg()->next(15));
 
 reg_def XMM11 ( SOC, SOE, Op_RegF, 11, xmm11->as_VMReg());
 reg_def XMM11b( SOC, SOE, Op_RegF, 11, xmm11->as_VMReg()->next(1));
@@ -179,6 +271,14 @@
 reg_def XMM11f( SOC, SOE, Op_RegF, 11, xmm11->as_VMReg()->next(5));
 reg_def XMM11g( SOC, SOE, Op_RegF, 11, xmm11->as_VMReg()->next(6));
 reg_def XMM11h( SOC, SOE, Op_RegF, 11, xmm11->as_VMReg()->next(7));
+reg_def XMM11i( SOC, SOE, Op_RegF, 11, xmm11->as_VMReg()->next(8));
+reg_def XMM11j( SOC, SOE, Op_RegF, 11, xmm11->as_VMReg()->next(9));
+reg_def XMM11k( SOC, SOE, Op_RegF, 11, xmm11->as_VMReg()->next(10));
+reg_def XMM11l( SOC, SOE, Op_RegF, 11, xmm11->as_VMReg()->next(11));
+reg_def XMM11m( SOC, SOE, Op_RegF, 11, xmm11->as_VMReg()->next(12));
+reg_def XMM11n( SOC, SOE, Op_RegF, 11, xmm11->as_VMReg()->next(13));
+reg_def XMM11o( SOC, SOE, Op_RegF, 11, xmm11->as_VMReg()->next(14));
+reg_def XMM11p( SOC, SOE, Op_RegF, 11, xmm11->as_VMReg()->next(15));
 
 reg_def XMM12 ( SOC, SOE, Op_RegF, 12, xmm12->as_VMReg());
 reg_def XMM12b( SOC, SOE, Op_RegF, 12, xmm12->as_VMReg()->next(1));
@@ -188,6 +288,14 @@
 reg_def XMM12f( SOC, SOE, Op_RegF, 12, xmm12->as_VMReg()->next(5));
 reg_def XMM12g( SOC, SOE, Op_RegF, 12, xmm12->as_VMReg()->next(6));
 reg_def XMM12h( SOC, SOE, Op_RegF, 12, xmm12->as_VMReg()->next(7));
+reg_def XMM12i( SOC, SOE, Op_RegF, 12, xmm12->as_VMReg()->next(8));
+reg_def XMM12j( SOC, SOE, Op_RegF, 12, xmm12->as_VMReg()->next(9));
+reg_def XMM12k( SOC, SOE, Op_RegF, 12, xmm12->as_VMReg()->next(10));
+reg_def XMM12l( SOC, SOE, Op_RegF, 12, xmm12->as_VMReg()->next(11));
+reg_def XMM12m( SOC, SOE, Op_RegF, 12, xmm12->as_VMReg()->next(12));
+reg_def XMM12n( SOC, SOE, Op_RegF, 12, xmm12->as_VMReg()->next(13));
+reg_def XMM12o( SOC, SOE, Op_RegF, 12, xmm12->as_VMReg()->next(14));
+reg_def XMM12p( SOC, SOE, Op_RegF, 12, xmm12->as_VMReg()->next(15));
 
 reg_def XMM13 ( SOC, SOE, Op_RegF, 13, xmm13->as_VMReg());
 reg_def XMM13b( SOC, SOE, Op_RegF, 13, xmm13->as_VMReg()->next(1));
@@ -197,6 +305,14 @@
 reg_def XMM13f( SOC, SOE, Op_RegF, 13, xmm13->as_VMReg()->next(5));
 reg_def XMM13g( SOC, SOE, Op_RegF, 13, xmm13->as_VMReg()->next(6));
 reg_def XMM13h( SOC, SOE, Op_RegF, 13, xmm13->as_VMReg()->next(7));
+reg_def XMM13i( SOC, SOE, Op_RegF, 13, xmm13->as_VMReg()->next(8));
+reg_def XMM13j( SOC, SOE, Op_RegF, 13, xmm13->as_VMReg()->next(9));
+reg_def XMM13k( SOC, SOE, Op_RegF, 13, xmm13->as_VMReg()->next(10));
+reg_def XMM13l( SOC, SOE, Op_RegF, 13, xmm13->as_VMReg()->next(11));
+reg_def XMM13m( SOC, SOE, Op_RegF, 13, xmm13->as_VMReg()->next(12));
+reg_def XMM13n( SOC, SOE, Op_RegF, 13, xmm13->as_VMReg()->next(13));
+reg_def XMM13o( SOC, SOE, Op_RegF, 13, xmm13->as_VMReg()->next(14));
+reg_def XMM13p( SOC, SOE, Op_RegF, 13, xmm13->as_VMReg()->next(15));
 
 reg_def XMM14 ( SOC, SOE, Op_RegF, 14, xmm14->as_VMReg());
 reg_def XMM14b( SOC, SOE, Op_RegF, 14, xmm14->as_VMReg()->next(1));
@@ -206,6 +322,14 @@
 reg_def XMM14f( SOC, SOE, Op_RegF, 14, xmm14->as_VMReg()->next(5));
 reg_def XMM14g( SOC, SOE, Op_RegF, 14, xmm14->as_VMReg()->next(6));
 reg_def XMM14h( SOC, SOE, Op_RegF, 14, xmm14->as_VMReg()->next(7));
+reg_def XMM14i( SOC, SOE, Op_RegF, 14, xmm14->as_VMReg()->next(8));
+reg_def XMM14j( SOC, SOE, Op_RegF, 14, xmm14->as_VMReg()->next(9));
+reg_def XMM14k( SOC, SOE, Op_RegF, 14, xmm14->as_VMReg()->next(10));
+reg_def XMM14l( SOC, SOE, Op_RegF, 14, xmm14->as_VMReg()->next(11));
+reg_def XMM14m( SOC, SOE, Op_RegF, 14, xmm14->as_VMReg()->next(12));
+reg_def XMM14n( SOC, SOE, Op_RegF, 14, xmm14->as_VMReg()->next(13));
+reg_def XMM14o( SOC, SOE, Op_RegF, 14, xmm14->as_VMReg()->next(14));
+reg_def XMM14p( SOC, SOE, Op_RegF, 14, xmm14->as_VMReg()->next(15));
 
 reg_def XMM15 ( SOC, SOE, Op_RegF, 15, xmm15->as_VMReg());
 reg_def XMM15b( SOC, SOE, Op_RegF, 15, xmm15->as_VMReg()->next(1));
@@ -215,6 +339,285 @@
 reg_def XMM15f( SOC, SOE, Op_RegF, 15, xmm15->as_VMReg()->next(5));
 reg_def XMM15g( SOC, SOE, Op_RegF, 15, xmm15->as_VMReg()->next(6));
 reg_def XMM15h( SOC, SOE, Op_RegF, 15, xmm15->as_VMReg()->next(7));
+reg_def XMM15i( SOC, SOE, Op_RegF, 15, xmm15->as_VMReg()->next(8));
+reg_def XMM15j( SOC, SOE, Op_RegF, 15, xmm15->as_VMReg()->next(9));
+reg_def XMM15k( SOC, SOE, Op_RegF, 15, xmm15->as_VMReg()->next(10));
+reg_def XMM15l( SOC, SOE, Op_RegF, 15, xmm15->as_VMReg()->next(11));
+reg_def XMM15m( SOC, SOE, Op_RegF, 15, xmm15->as_VMReg()->next(12));
+reg_def XMM15n( SOC, SOE, Op_RegF, 15, xmm15->as_VMReg()->next(13));
+reg_def XMM15o( SOC, SOE, Op_RegF, 15, xmm15->as_VMReg()->next(14));
+reg_def XMM15p( SOC, SOE, Op_RegF, 15, xmm15->as_VMReg()->next(15));
+
+reg_def XMM16 ( SOC, SOE, Op_RegF, 16, xmm16->as_VMReg());
+reg_def XMM16b( SOC, SOE, Op_RegF, 16, xmm16->as_VMReg()->next(1));
+reg_def XMM16c( SOC, SOE, Op_RegF, 16, xmm16->as_VMReg()->next(2));
+reg_def XMM16d( SOC, SOE, Op_RegF, 16, xmm16->as_VMReg()->next(3));
+reg_def XMM16e( SOC, SOE, Op_RegF, 16, xmm16->as_VMReg()->next(4));
+reg_def XMM16f( SOC, SOE, Op_RegF, 16, xmm16->as_VMReg()->next(5));
+reg_def XMM16g( SOC, SOE, Op_RegF, 16, xmm16->as_VMReg()->next(6));
+reg_def XMM16h( SOC, SOE, Op_RegF, 16, xmm16->as_VMReg()->next(7));
+reg_def XMM16i( SOC, SOE, Op_RegF, 16, xmm15->as_VMReg()->next(8));
+reg_def XMM16j( SOC, SOE, Op_RegF, 16, xmm16->as_VMReg()->next(9));
+reg_def XMM16k( SOC, SOE, Op_RegF, 16, xmm16->as_VMReg()->next(10));
+reg_def XMM16l( SOC, SOE, Op_RegF, 16, xmm16->as_VMReg()->next(11));
+reg_def XMM16m( SOC, SOE, Op_RegF, 16, xmm16->as_VMReg()->next(12));
+reg_def XMM16n( SOC, SOE, Op_RegF, 16, xmm16->as_VMReg()->next(13));
+reg_def XMM16o( SOC, SOE, Op_RegF, 16, xmm16->as_VMReg()->next(14));
+reg_def XMM16p( SOC, SOE, Op_RegF, 16, xmm16->as_VMReg()->next(15));
+
+reg_def XMM17 ( SOC, SOE, Op_RegF, 17, xmm17->as_VMReg());
+reg_def XMM17b( SOC, SOE, Op_RegF, 17, xmm17->as_VMReg()->next(1));
+reg_def XMM17c( SOC, SOE, Op_RegF, 17, xmm17->as_VMReg()->next(2));
+reg_def XMM17d( SOC, SOE, Op_RegF, 17, xmm17->as_VMReg()->next(3));
+reg_def XMM17e( SOC, SOE, Op_RegF, 17, xmm17->as_VMReg()->next(4));
+reg_def XMM17f( SOC, SOE, Op_RegF, 17, xmm17->as_VMReg()->next(5));
+reg_def XMM17g( SOC, SOE, Op_RegF, 17, xmm17->as_VMReg()->next(6));
+reg_def XMM17h( SOC, SOE, Op_RegF, 17, xmm17->as_VMReg()->next(7));
+reg_def XMM17i( SOC, SOE, Op_RegF, 17, xmm17->as_VMReg()->next(8));
+reg_def XMM17j( SOC, SOE, Op_RegF, 17, xmm17->as_VMReg()->next(9));
+reg_def XMM17k( SOC, SOE, Op_RegF, 17, xmm17->as_VMReg()->next(10));
+reg_def XMM17l( SOC, SOE, Op_RegF, 17, xmm17->as_VMReg()->next(11));
+reg_def XMM17m( SOC, SOE, Op_RegF, 17, xmm17->as_VMReg()->next(12));
+reg_def XMM17n( SOC, SOE, Op_RegF, 17, xmm17->as_VMReg()->next(13));
+reg_def XMM17o( SOC, SOE, Op_RegF, 17, xmm17->as_VMReg()->next(14));
+reg_def XMM17p( SOC, SOE, Op_RegF, 17, xmm17->as_VMReg()->next(15));
+
+reg_def XMM18 ( SOC, SOE, Op_RegF, 18, xmm18->as_VMReg());
+reg_def XMM18b( SOC, SOE, Op_RegF, 18, xmm18->as_VMReg()->next(1));
+reg_def XMM18c( SOC, SOE, Op_RegF, 18, xmm18->as_VMReg()->next(2));
+reg_def XMM18d( SOC, SOE, Op_RegF, 18, xmm18->as_VMReg()->next(3));
+reg_def XMM18e( SOC, SOE, Op_RegF, 18, xmm18->as_VMReg()->next(4));
+reg_def XMM18f( SOC, SOE, Op_RegF, 18, xmm18->as_VMReg()->next(5));
+reg_def XMM18g( SOC, SOE, Op_RegF, 18, xmm18->as_VMReg()->next(6));
+reg_def XMM18h( SOC, SOE, Op_RegF, 18, xmm18->as_VMReg()->next(7));
+reg_def XMM18i( SOC, SOE, Op_RegF, 18, xmm18->as_VMReg()->next(8));
+reg_def XMM18j( SOC, SOE, Op_RegF, 18, xmm18->as_VMReg()->next(9));
+reg_def XMM18k( SOC, SOE, Op_RegF, 18, xmm18->as_VMReg()->next(10));
+reg_def XMM18l( SOC, SOE, Op_RegF, 18, xmm18->as_VMReg()->next(11));
+reg_def XMM18m( SOC, SOE, Op_RegF, 18, xmm18->as_VMReg()->next(12));
+reg_def XMM18n( SOC, SOE, Op_RegF, 18, xmm18->as_VMReg()->next(13));
+reg_def XMM18o( SOC, SOE, Op_RegF, 18, xmm18->as_VMReg()->next(14));
+reg_def XMM18p( SOC, SOE, Op_RegF, 18, xmm18->as_VMReg()->next(15));
+
+reg_def XMM19 ( SOC, SOE, Op_RegF, 19, xmm19->as_VMReg());
+reg_def XMM19b( SOC, SOE, Op_RegF, 19, xmm19->as_VMReg()->next(1));
+reg_def XMM19c( SOC, SOE, Op_RegF, 19, xmm19->as_VMReg()->next(2));
+reg_def XMM19d( SOC, SOE, Op_RegF, 19, xmm19->as_VMReg()->next(3));
+reg_def XMM19e( SOC, SOE, Op_RegF, 19, xmm19->as_VMReg()->next(4));
+reg_def XMM19f( SOC, SOE, Op_RegF, 19, xmm19->as_VMReg()->next(5));
+reg_def XMM19g( SOC, SOE, Op_RegF, 19, xmm19->as_VMReg()->next(6));
+reg_def XMM19h( SOC, SOE, Op_RegF, 19, xmm19->as_VMReg()->next(7));
+reg_def XMM19i( SOC, SOE, Op_RegF, 19, xmm19->as_VMReg()->next(8));
+reg_def XMM19j( SOC, SOE, Op_RegF, 19, xmm19->as_VMReg()->next(9));
+reg_def XMM19k( SOC, SOE, Op_RegF, 19, xmm19->as_VMReg()->next(10));
+reg_def XMM19l( SOC, SOE, Op_RegF, 19, xmm19->as_VMReg()->next(11));
+reg_def XMM19m( SOC, SOE, Op_RegF, 19, xmm19->as_VMReg()->next(12));
+reg_def XMM19n( SOC, SOE, Op_RegF, 19, xmm19->as_VMReg()->next(13));
+reg_def XMM19o( SOC, SOE, Op_RegF, 19, xmm19->as_VMReg()->next(14));
+reg_def XMM19p( SOC, SOE, Op_RegF, 19, xmm19->as_VMReg()->next(15));
+
+reg_def XMM20 ( SOC, SOE, Op_RegF, 20, xmm20->as_VMReg());
+reg_def XMM20b( SOC, SOE, Op_RegF, 20, xmm20->as_VMReg()->next(1));
+reg_def XMM20c( SOC, SOE, Op_RegF, 20, xmm20->as_VMReg()->next(2));
+reg_def XMM20d( SOC, SOE, Op_RegF, 20, xmm20->as_VMReg()->next(3));
+reg_def XMM20e( SOC, SOE, Op_RegF, 20, xmm20->as_VMReg()->next(4));
+reg_def XMM20f( SOC, SOE, Op_RegF, 20, xmm20->as_VMReg()->next(5));
+reg_def XMM20g( SOC, SOE, Op_RegF, 20, xmm20->as_VMReg()->next(6));
+reg_def XMM20h( SOC, SOE, Op_RegF, 20, xmm20->as_VMReg()->next(7));
+reg_def XMM20i( SOC, SOE, Op_RegF, 20, xmm20->as_VMReg()->next(8));
+reg_def XMM20j( SOC, SOE, Op_RegF, 20, xmm20->as_VMReg()->next(9));
+reg_def XMM20k( SOC, SOE, Op_RegF, 20, xmm20->as_VMReg()->next(10));
+reg_def XMM20l( SOC, SOE, Op_RegF, 20, xmm20->as_VMReg()->next(11));
+reg_def XMM20m( SOC, SOE, Op_RegF, 20, xmm20->as_VMReg()->next(12));
+reg_def XMM20n( SOC, SOE, Op_RegF, 20, xmm20->as_VMReg()->next(13));
+reg_def XMM20o( SOC, SOE, Op_RegF, 20, xmm20->as_VMReg()->next(14));
+reg_def XMM20p( SOC, SOE, Op_RegF, 20, xmm20->as_VMReg()->next(15));
+
+reg_def XMM21 ( SOC, SOE, Op_RegF, 21, xmm21->as_VMReg());
+reg_def XMM21b( SOC, SOE, Op_RegF, 21, xmm21->as_VMReg()->next(1));
+reg_def XMM21c( SOC, SOE, Op_RegF, 21, xmm21->as_VMReg()->next(2));
+reg_def XMM21d( SOC, SOE, Op_RegF, 21, xmm21->as_VMReg()->next(3));
+reg_def XMM21e( SOC, SOE, Op_RegF, 21, xmm21->as_VMReg()->next(4));
+reg_def XMM21f( SOC, SOE, Op_RegF, 21, xmm21->as_VMReg()->next(5));
+reg_def XMM21g( SOC, SOE, Op_RegF, 21, xmm21->as_VMReg()->next(6));
+reg_def XMM21h( SOC, SOE, Op_RegF, 21, xmm21->as_VMReg()->next(7));
+reg_def XMM21i( SOC, SOE, Op_RegF, 21, xmm21->as_VMReg()->next(8));
+reg_def XMM21j( SOC, SOE, Op_RegF, 21, xmm21->as_VMReg()->next(9));
+reg_def XMM21k( SOC, SOE, Op_RegF, 21, xmm21->as_VMReg()->next(10));
+reg_def XMM21l( SOC, SOE, Op_RegF, 21, xmm21->as_VMReg()->next(11));
+reg_def XMM21m( SOC, SOE, Op_RegF, 21, xmm21->as_VMReg()->next(12));
+reg_def XMM21n( SOC, SOE, Op_RegF, 21, xmm21->as_VMReg()->next(13));
+reg_def XMM21o( SOC, SOE, Op_RegF, 21, xmm21->as_VMReg()->next(14));
+reg_def XMM21p( SOC, SOE, Op_RegF, 21, xmm21->as_VMReg()->next(15));
+
+reg_def XMM22 ( SOC, SOE, Op_RegF, 22, xmm22->as_VMReg());
+reg_def XMM22b( SOC, SOE, Op_RegF, 22, xmm22->as_VMReg()->next(1));
+reg_def XMM22c( SOC, SOE, Op_RegF, 22, xmm22->as_VMReg()->next(2));
+reg_def XMM22d( SOC, SOE, Op_RegF, 22, xmm22->as_VMReg()->next(3));
+reg_def XMM22e( SOC, SOE, Op_RegF, 22, xmm22->as_VMReg()->next(4));
+reg_def XMM22f( SOC, SOE, Op_RegF, 22, xmm22->as_VMReg()->next(5));
+reg_def XMM22g( SOC, SOE, Op_RegF, 22, xmm22->as_VMReg()->next(6));
+reg_def XMM22h( SOC, SOE, Op_RegF, 22, xmm22->as_VMReg()->next(7));
+reg_def XMM22i( SOC, SOE, Op_RegF, 22, xmm22->as_VMReg()->next(8));
+reg_def XMM22j( SOC, SOE, Op_RegF, 22, xmm22->as_VMReg()->next(9));
+reg_def XMM22k( SOC, SOE, Op_RegF, 22, xmm22->as_VMReg()->next(10));
+reg_def XMM22l( SOC, SOE, Op_RegF, 22, xmm22->as_VMReg()->next(11));
+reg_def XMM22m( SOC, SOE, Op_RegF, 22, xmm22->as_VMReg()->next(12));
+reg_def XMM22n( SOC, SOE, Op_RegF, 22, xmm22->as_VMReg()->next(13));
+reg_def XMM22o( SOC, SOE, Op_RegF, 22, xmm22->as_VMReg()->next(14));
+reg_def XMM22p( SOC, SOE, Op_RegF, 22, xmm22->as_VMReg()->next(15));
+
+reg_def XMM23 ( SOC, SOE, Op_RegF, 23, xmm23->as_VMReg());
+reg_def XMM23b( SOC, SOE, Op_RegF, 23, xmm23->as_VMReg()->next(1));
+reg_def XMM23c( SOC, SOE, Op_RegF, 23, xmm23->as_VMReg()->next(2));
+reg_def XMM23d( SOC, SOE, Op_RegF, 23, xmm23->as_VMReg()->next(3));
+reg_def XMM23e( SOC, SOE, Op_RegF, 23, xmm23->as_VMReg()->next(4));
+reg_def XMM23f( SOC, SOE, Op_RegF, 23, xmm23->as_VMReg()->next(5));
+reg_def XMM23g( SOC, SOE, Op_RegF, 23, xmm23->as_VMReg()->next(6));
+reg_def XMM23h( SOC, SOE, Op_RegF, 23, xmm23->as_VMReg()->next(7));
+reg_def XMM23i( SOC, SOE, Op_RegF, 23, xmm23->as_VMReg()->next(8));
+reg_def XMM23j( SOC, SOE, Op_RegF, 23, xmm23->as_VMReg()->next(9));
+reg_def XMM23k( SOC, SOE, Op_RegF, 23, xmm23->as_VMReg()->next(10));
+reg_def XMM23l( SOC, SOE, Op_RegF, 23, xmm23->as_VMReg()->next(11));
+reg_def XMM23m( SOC, SOE, Op_RegF, 23, xmm23->as_VMReg()->next(12));
+reg_def XMM23n( SOC, SOE, Op_RegF, 23, xmm23->as_VMReg()->next(13));
+reg_def XMM23o( SOC, SOE, Op_RegF, 23, xmm23->as_VMReg()->next(14));
+reg_def XMM23p( SOC, SOE, Op_RegF, 23, xmm23->as_VMReg()->next(15));
+
+reg_def XMM24 ( SOC, SOE, Op_RegF, 24, xmm24->as_VMReg());
+reg_def XMM24b( SOC, SOE, Op_RegF, 24, xmm24->as_VMReg()->next(1));
+reg_def XMM24c( SOC, SOE, Op_RegF, 24, xmm24->as_VMReg()->next(2));
+reg_def XMM24d( SOC, SOE, Op_RegF, 24, xmm24->as_VMReg()->next(3));
+reg_def XMM24e( SOC, SOE, Op_RegF, 24, xmm24->as_VMReg()->next(4));
+reg_def XMM24f( SOC, SOE, Op_RegF, 24, xmm24->as_VMReg()->next(5));
+reg_def XMM24g( SOC, SOE, Op_RegF, 24, xmm24->as_VMReg()->next(6));
+reg_def XMM24h( SOC, SOE, Op_RegF, 24, xmm24->as_VMReg()->next(7));
+reg_def XMM24i( SOC, SOE, Op_RegF, 24, xmm24->as_VMReg()->next(8));
+reg_def XMM24j( SOC, SOE, Op_RegF, 24, xmm24->as_VMReg()->next(9));
+reg_def XMM24k( SOC, SOE, Op_RegF, 24, xmm24->as_VMReg()->next(10));
+reg_def XMM24l( SOC, SOE, Op_RegF, 24, xmm24->as_VMReg()->next(11));
+reg_def XMM24m( SOC, SOE, Op_RegF, 24, xmm24->as_VMReg()->next(12));
+reg_def XMM24n( SOC, SOE, Op_RegF, 24, xmm24->as_VMReg()->next(13));
+reg_def XMM24o( SOC, SOE, Op_RegF, 24, xmm24->as_VMReg()->next(14));
+reg_def XMM24p( SOC, SOE, Op_RegF, 24, xmm24->as_VMReg()->next(15));
+
+reg_def XMM25 ( SOC, SOE, Op_RegF, 25, xmm25->as_VMReg());
+reg_def XMM25b( SOC, SOE, Op_RegF, 25, xmm25->as_VMReg()->next(1));
+reg_def XMM25c( SOC, SOE, Op_RegF, 25, xmm25->as_VMReg()->next(2));
+reg_def XMM25d( SOC, SOE, Op_RegF, 25, xmm25->as_VMReg()->next(3));
+reg_def XMM25e( SOC, SOE, Op_RegF, 25, xmm25->as_VMReg()->next(4));
+reg_def XMM25f( SOC, SOE, Op_RegF, 25, xmm25->as_VMReg()->next(5));
+reg_def XMM25g( SOC, SOE, Op_RegF, 25, xmm25->as_VMReg()->next(6));
+reg_def XMM25h( SOC, SOE, Op_RegF, 25, xmm25->as_VMReg()->next(7));
+reg_def XMM25i( SOC, SOE, Op_RegF, 25, xmm25->as_VMReg()->next(8));
+reg_def XMM25j( SOC, SOE, Op_RegF, 25, xmm25->as_VMReg()->next(9));
+reg_def XMM25k( SOC, SOE, Op_RegF, 25, xmm25->as_VMReg()->next(10));
+reg_def XMM25l( SOC, SOE, Op_RegF, 25, xmm25->as_VMReg()->next(11));
+reg_def XMM25m( SOC, SOE, Op_RegF, 25, xmm25->as_VMReg()->next(12));
+reg_def XMM25n( SOC, SOE, Op_RegF, 25, xmm25->as_VMReg()->next(13));
+reg_def XMM25o( SOC, SOE, Op_RegF, 25, xmm25->as_VMReg()->next(14));
+reg_def XMM25p( SOC, SOE, Op_RegF, 25, xmm25->as_VMReg()->next(15));
+
+reg_def XMM26 ( SOC, SOE, Op_RegF, 26, xmm26->as_VMReg());
+reg_def XMM26b( SOC, SOE, Op_RegF, 26, xmm26->as_VMReg()->next(1));
+reg_def XMM26c( SOC, SOE, Op_RegF, 26, xmm26->as_VMReg()->next(2));
+reg_def XMM26d( SOC, SOE, Op_RegF, 26, xmm26->as_VMReg()->next(3));
+reg_def XMM26e( SOC, SOE, Op_RegF, 26, xmm26->as_VMReg()->next(4));
+reg_def XMM26f( SOC, SOE, Op_RegF, 26, xmm26->as_VMReg()->next(5));
+reg_def XMM26g( SOC, SOE, Op_RegF, 26, xmm26->as_VMReg()->next(6));
+reg_def XMM26h( SOC, SOE, Op_RegF, 26, xmm26->as_VMReg()->next(7));
+reg_def XMM26i( SOC, SOE, Op_RegF, 26, xmm26->as_VMReg()->next(8));
+reg_def XMM26j( SOC, SOE, Op_RegF, 26, xmm26->as_VMReg()->next(9));
+reg_def XMM26k( SOC, SOE, Op_RegF, 26, xmm26->as_VMReg()->next(10));
+reg_def XMM26l( SOC, SOE, Op_RegF, 26, xmm26->as_VMReg()->next(11));
+reg_def XMM26m( SOC, SOE, Op_RegF, 26, xmm26->as_VMReg()->next(12));
+reg_def XMM26n( SOC, SOE, Op_RegF, 26, xmm26->as_VMReg()->next(13));
+reg_def XMM26o( SOC, SOE, Op_RegF, 26, xmm26->as_VMReg()->next(14));
+reg_def XMM26p( SOC, SOE, Op_RegF, 26, xmm26->as_VMReg()->next(15));
+
+reg_def XMM27g( SOC, SOE, Op_RegF, 27, xmm27->as_VMReg()->next(1));
+reg_def XMM27c( SOC, SOE, Op_RegF, 27, xmm27->as_VMReg()->next(2));
+reg_def XMM27d( SOC, SOE, Op_RegF, 27, xmm27->as_VMReg()->next(3));
+reg_def XMM27e( SOC, SOE, Op_RegF, 27, xmm27->as_VMReg()->next(4));
+reg_def XMM27f( SOC, SOE, Op_RegF, 27, xmm27->as_VMReg()->next(5));
+reg_def XMM27g( SOC, SOE, Op_RegF, 27, xmm27->as_VMReg()->next(6));
+reg_def XMM27h( SOC, SOE, Op_RegF, 27, xmm27->as_VMReg()->next(7));
+reg_def XMM27i( SOC, SOE, Op_RegF, 27, xmm27->as_VMReg()->next(8));
+reg_def XMM27j( SOC, SOE, Op_RegF, 27, xmm27->as_VMReg()->next(9));
+reg_def XMM27k( SOC, SOE, Op_RegF, 27, xmm27->as_VMReg()->next(10));
+reg_def XMM27l( SOC, SOE, Op_RegF, 27, xmm27->as_VMReg()->next(11));
+reg_def XMM27m( SOC, SOE, Op_RegF, 27, xmm27->as_VMReg()->next(12));
+reg_def XMM27n( SOC, SOE, Op_RegF, 27, xmm27->as_VMReg()->next(13));
+reg_def XMM27o( SOC, SOE, Op_RegF, 27, xmm27->as_VMReg()->next(14));
+reg_def XMM27p( SOC, SOE, Op_RegF, 27, xmm27->as_VMReg()->next(15));
+
+reg_def XMM28 ( SOC, SOE, Op_RegF, 28, xmm28->as_VMReg());
+reg_def XMM28b( SOC, SOE, Op_RegF, 28, xmm28->as_VMReg()->next(1));
+reg_def XMM28c( SOC, SOE, Op_RegF, 28, xmm28->as_VMReg()->next(2));
+reg_def XMM28d( SOC, SOE, Op_RegF, 28, xmm28->as_VMReg()->next(3));
+reg_def XMM28e( SOC, SOE, Op_RegF, 28, xmm28->as_VMReg()->next(4));
+reg_def XMM28f( SOC, SOE, Op_RegF, 28, xmm28->as_VMReg()->next(5));
+reg_def XMM28g( SOC, SOE, Op_RegF, 28, xmm28->as_VMReg()->next(6));
+reg_def XMM28h( SOC, SOE, Op_RegF, 28, xmm28->as_VMReg()->next(7));
+reg_def XMM28i( SOC, SOE, Op_RegF, 28, xmm28->as_VMReg()->next(8));
+reg_def XMM28j( SOC, SOE, Op_RegF, 28, xmm28->as_VMReg()->next(9));
+reg_def XMM28k( SOC, SOE, Op_RegF, 28, xmm28->as_VMReg()->next(10));
+reg_def XMM28l( SOC, SOE, Op_RegF, 28, xmm28->as_VMReg()->next(11));
+reg_def XMM28m( SOC, SOE, Op_RegF, 28, xmm28->as_VMReg()->next(12));
+reg_def XMM28n( SOC, SOE, Op_RegF, 28, xmm28->as_VMReg()->next(13));
+reg_def XMM28o( SOC, SOE, Op_RegF, 28, xmm28->as_VMReg()->next(14));
+reg_def XMM28p( SOC, SOE, Op_RegF, 28, xmm28->as_VMReg()->next(15));
+
+reg_def XMM29 ( SOC, SOE, Op_RegF, 29, xmm29->as_VMReg());
+reg_def XMM29b( SOC, SOE, Op_RegF, 29, xmm29->as_VMReg()->next(1));
+reg_def XMM29c( SOC, SOE, Op_RegF, 29, xmm29->as_VMReg()->next(2));
+reg_def XMM29d( SOC, SOE, Op_RegF, 29, xmm29->as_VMReg()->next(3));
+reg_def XMM29e( SOC, SOE, Op_RegF, 29, xmm29->as_VMReg()->next(4));
+reg_def XMM29f( SOC, SOE, Op_RegF, 29, xmm29->as_VMReg()->next(5));
+reg_def XMM29g( SOC, SOE, Op_RegF, 29, xmm29->as_VMReg()->next(6));
+reg_def XMM29h( SOC, SOE, Op_RegF, 29, xmm29->as_VMReg()->next(7));
+reg_def XMM29i( SOC, SOE, Op_RegF, 29, xmm29->as_VMReg()->next(8));
+reg_def XMM29j( SOC, SOE, Op_RegF, 29, xmm29->as_VMReg()->next(9));
+reg_def XMM29k( SOC, SOE, Op_RegF, 29, xmm29->as_VMReg()->next(10));
+reg_def XMM29l( SOC, SOE, Op_RegF, 29, xmm29->as_VMReg()->next(11));
+reg_def XMM29m( SOC, SOE, Op_RegF, 29, xmm29->as_VMReg()->next(12));
+reg_def XMM29n( SOC, SOE, Op_RegF, 29, xmm29->as_VMReg()->next(13));
+reg_def XMM29o( SOC, SOE, Op_RegF, 29, xmm29->as_VMReg()->next(14));
+reg_def XMM29p( SOC, SOE, Op_RegF, 29, xmm29->as_VMReg()->next(15));
+
+reg_def XMM30 ( SOC, SOE, Op_RegF, 30, xmm30->as_VMReg());
+reg_def XMM30b( SOC, SOE, Op_RegF, 30, xmm30->as_VMReg()->next(1));
+reg_def XMM30c( SOC, SOE, Op_RegF, 30, xmm30->as_VMReg()->next(2));
+reg_def XMM30d( SOC, SOE, Op_RegF, 30, xmm30->as_VMReg()->next(3));
+reg_def XMM30e( SOC, SOE, Op_RegF, 30, xmm30->as_VMReg()->next(4));
+reg_def XMM30f( SOC, SOE, Op_RegF, 30, xmm30->as_VMReg()->next(5));
+reg_def XMM30g( SOC, SOE, Op_RegF, 30, xmm30->as_VMReg()->next(6));
+reg_def XMM30h( SOC, SOE, Op_RegF, 30, xmm30->as_VMReg()->next(7));
+reg_def XMM30i( SOC, SOE, Op_RegF, 30, xmm30->as_VMReg()->next(8));
+reg_def XMM30j( SOC, SOE, Op_RegF, 30, xmm30->as_VMReg()->next(9));
+reg_def XMM30k( SOC, SOE, Op_RegF, 30, xmm30->as_VMReg()->next(10));
+reg_def XMM30l( SOC, SOE, Op_RegF, 30, xmm30->as_VMReg()->next(11));
+reg_def XMM30m( SOC, SOE, Op_RegF, 30, xmm30->as_VMReg()->next(12));
+reg_def XMM30n( SOC, SOE, Op_RegF, 30, xmm30->as_VMReg()->next(13));
+reg_def XMM30o( SOC, SOE, Op_RegF, 30, xmm30->as_VMReg()->next(14));
+reg_def XMM30p( SOC, SOE, Op_RegF, 30, xmm30->as_VMReg()->next(15));
+
+reg_def XMM31 ( SOC, SOE, Op_RegF, 31, xmm31->as_VMReg());
+reg_def XMM31b( SOC, SOE, Op_RegF, 31, xmm31->as_VMReg()->next(1));
+reg_def XMM31c( SOC, SOE, Op_RegF, 31, xmm31->as_VMReg()->next(2));
+reg_def XMM31d( SOC, SOE, Op_RegF, 31, xmm31->as_VMReg()->next(3));
+reg_def XMM31e( SOC, SOE, Op_RegF, 31, xmm31->as_VMReg()->next(4));
+reg_def XMM31f( SOC, SOE, Op_RegF, 31, xmm31->as_VMReg()->next(5));
+reg_def XMM31g( SOC, SOE, Op_RegF, 31, xmm31->as_VMReg()->next(6));
+reg_def XMM31h( SOC, SOE, Op_RegF, 31, xmm31>-as_VMReg()->next(7));
+reg_def XMM31i( SOC, SOE, Op_RegF, 31, xmm31->as_VMReg()->next(8));
+reg_def XMM31j( SOC, SOE, Op_RegF, 31, xmm31->as_VMReg()->next(9));
+reg_def XMM31k( SOC, SOE, Op_RegF, 31, xmm31->as_VMReg()->next(10));
+reg_def XMM31l( SOC, SOE, Op_RegF, 31, xmm31->as_VMReg()->next(11));
+reg_def XMM31m( SOC, SOE, Op_RegF, 31, xmm31->as_VMReg()->next(12));
+reg_def XMM31n( SOC, SOE, Op_RegF, 31, xmm31->as_VMReg()->next(13));
+reg_def XMM31o( SOC, SOE, Op_RegF, 31, xmm31->as_VMReg()->next(14));
+reg_def XMM31p( SOC, SOE, Op_RegF, 31, xmm31->as_VMReg()->next(15));
 
 #else // _WIN64
 
@@ -226,6 +629,14 @@
 reg_def XMM6f( SOC, SOC, Op_RegF, 6, xmm6->as_VMReg()->next(5));
 reg_def XMM6g( SOC, SOC, Op_RegF, 6, xmm6->as_VMReg()->next(6));
 reg_def XMM6h( SOC, SOC, Op_RegF, 6, xmm6->as_VMReg()->next(7));
+reg_def XMM6i( SOC, SOC, Op_RegF, 6, xmm6->as_VMReg()->next(8));
+reg_def XMM6j( SOC, SOC, Op_RegF, 6, xmm6->as_VMReg()->next(9));
+reg_def XMM6k( SOC, SOC, Op_RegF, 6, xmm6->as_VMReg()->next(10));
+reg_def XMM6l( SOC, SOC, Op_RegF, 6, xmm6->as_VMReg()->next(11));
+reg_def XMM6m( SOC, SOC, Op_RegF, 6, xmm6->as_VMReg()->next(12));
+reg_def XMM6n( SOC, SOC, Op_RegF, 6, xmm6->as_VMReg()->next(13));
+reg_def XMM6o( SOC, SOC, Op_RegF, 6, xmm6->as_VMReg()->next(14));
+reg_def XMM6p( SOC, SOC, Op_RegF, 6, xmm6->as_VMReg()->next(15));
 
 reg_def XMM7 ( SOC, SOC, Op_RegF, 7, xmm7->as_VMReg());
 reg_def XMM7b( SOC, SOC, Op_RegF, 7, xmm7->as_VMReg()->next(1));
@@ -235,6 +646,14 @@
 reg_def XMM7f( SOC, SOC, Op_RegF, 7, xmm7->as_VMReg()->next(5));
 reg_def XMM7g( SOC, SOC, Op_RegF, 7, xmm7->as_VMReg()->next(6));
 reg_def XMM7h( SOC, SOC, Op_RegF, 7, xmm7->as_VMReg()->next(7));
+reg_def XMM7i( SOC, SOC, Op_RegF, 7, xmm7->as_VMReg()->next(8));
+reg_def XMM7j( SOC, SOC, Op_RegF, 7, xmm7->as_VMReg()->next(9));
+reg_def XMM7k( SOC, SOC, Op_RegF, 7, xmm7->as_VMReg()->next(10));
+reg_def XMM7l( SOC, SOC, Op_RegF, 7, xmm7->as_VMReg()->next(11));
+reg_def XMM7m( SOC, SOC, Op_RegF, 7, xmm7->as_VMReg()->next(12));
+reg_def XMM7n( SOC, SOC, Op_RegF, 7, xmm7->as_VMReg()->next(13));
+reg_def XMM7o( SOC, SOC, Op_RegF, 7, xmm7->as_VMReg()->next(14));
+reg_def XMM7p( SOC, SOC, Op_RegF, 7, xmm7->as_VMReg()->next(15));
 
 #ifdef _LP64
 
@@ -246,6 +665,14 @@
 reg_def XMM8f( SOC, SOC, Op_RegF, 8, xmm8->as_VMReg()->next(5));
 reg_def XMM8g( SOC, SOC, Op_RegF, 8, xmm8->as_VMReg()->next(6));
 reg_def XMM8h( SOC, SOC, Op_RegF, 8, xmm8->as_VMReg()->next(7));
+reg_def XMM8i( SOC, SOC, Op_RegF, 8, xmm8->as_VMReg()->next(8));
+reg_def XMM8j( SOC, SOC, Op_RegF, 8, xmm8->as_VMReg()->next(9));
+reg_def XMM8k( SOC, SOC, Op_RegF, 8, xmm8->as_VMReg()->next(10));
+reg_def XMM8l( SOC, SOC, Op_RegF, 8, xmm8->as_VMReg()->next(11));
+reg_def XMM8m( SOC, SOC, Op_RegF, 8, xmm8->as_VMReg()->next(12));
+reg_def XMM8n( SOC, SOC, Op_RegF, 8, xmm8->as_VMReg()->next(13));
+reg_def XMM8o( SOC, SOC, Op_RegF, 8, xmm8->as_VMReg()->next(14));
+reg_def XMM8p( SOC, SOC, Op_RegF, 8, xmm8->as_VMReg()->next(15));
 
 reg_def XMM9 ( SOC, SOC, Op_RegF, 9, xmm9->as_VMReg());
 reg_def XMM9b( SOC, SOC, Op_RegF, 9, xmm9->as_VMReg()->next(1));
@@ -255,6 +682,14 @@
 reg_def XMM9f( SOC, SOC, Op_RegF, 9, xmm9->as_VMReg()->next(5));
 reg_def XMM9g( SOC, SOC, Op_RegF, 9, xmm9->as_VMReg()->next(6));
 reg_def XMM9h( SOC, SOC, Op_RegF, 9, xmm9->as_VMReg()->next(7));
+reg_def XMM9i( SOC, SOC, Op_RegF, 9, xmm9->as_VMReg()->next(8));
+reg_def XMM9j( SOC, SOC, Op_RegF, 9, xmm9->as_VMReg()->next(9));
+reg_def XMM9k( SOC, SOC, Op_RegF, 9, xmm9->as_VMReg()->next(10));
+reg_def XMM9l( SOC, SOC, Op_RegF, 9, xmm9->as_VMReg()->next(11));
+reg_def XMM9m( SOC, SOC, Op_RegF, 9, xmm9->as_VMReg()->next(12));
+reg_def XMM9n( SOC, SOC, Op_RegF, 9, xmm9->as_VMReg()->next(13));
+reg_def XMM9o( SOC, SOC, Op_RegF, 9, xmm9->as_VMReg()->next(14));
+reg_def XMM9p( SOC, SOC, Op_RegF, 9, xmm9->as_VMReg()->next(15));
 
 reg_def XMM10 ( SOC, SOC, Op_RegF, 10, xmm10->as_VMReg());
 reg_def XMM10b( SOC, SOC, Op_RegF, 10, xmm10->as_VMReg()->next(1));
@@ -264,6 +699,14 @@
 reg_def XMM10f( SOC, SOC, Op_RegF, 10, xmm10->as_VMReg()->next(5));
 reg_def XMM10g( SOC, SOC, Op_RegF, 10, xmm10->as_VMReg()->next(6));
 reg_def XMM10h( SOC, SOC, Op_RegF, 10, xmm10->as_VMReg()->next(7));
+reg_def XMM10i( SOC, SOC, Op_RegF, 10, xmm10->as_VMReg()->next(8));
+reg_def XMM10j( SOC, SOC, Op_RegF, 10, xmm10->as_VMReg()->next(9));
+reg_def XMM10k( SOC, SOC, Op_RegF, 10, xmm10->as_VMReg()->next(10));
+reg_def XMM10l( SOC, SOC, Op_RegF, 10, xmm10->as_VMReg()->next(11));
+reg_def XMM10m( SOC, SOC, Op_RegF, 10, xmm10->as_VMReg()->next(12));
+reg_def XMM10n( SOC, SOC, Op_RegF, 10, xmm10->as_VMReg()->next(13));
+reg_def XMM10o( SOC, SOC, Op_RegF, 10, xmm10->as_VMReg()->next(14));
+reg_def XMM10p( SOC, SOC, Op_RegF, 10, xmm10->as_VMReg()->next(15));
 
 reg_def XMM11 ( SOC, SOC, Op_RegF, 11, xmm11->as_VMReg());
 reg_def XMM11b( SOC, SOC, Op_RegF, 11, xmm11->as_VMReg()->next(1));
@@ -273,6 +716,14 @@
 reg_def XMM11f( SOC, SOC, Op_RegF, 11, xmm11->as_VMReg()->next(5));
 reg_def XMM11g( SOC, SOC, Op_RegF, 11, xmm11->as_VMReg()->next(6));
 reg_def XMM11h( SOC, SOC, Op_RegF, 11, xmm11->as_VMReg()->next(7));
+reg_def XMM11i( SOC, SOC, Op_RegF, 11, xmm11->as_VMReg()->next(8));
+reg_def XMM11j( SOC, SOC, Op_RegF, 11, xmm11->as_VMReg()->next(9));
+reg_def XMM11k( SOC, SOC, Op_RegF, 11, xmm11->as_VMReg()->next(10));
+reg_def XMM11l( SOC, SOC, Op_RegF, 11, xmm11->as_VMReg()->next(11));
+reg_def XMM11m( SOC, SOC, Op_RegF, 11, xmm11->as_VMReg()->next(12));
+reg_def XMM11n( SOC, SOC, Op_RegF, 11, xmm11->as_VMReg()->next(13));
+reg_def XMM11o( SOC, SOC, Op_RegF, 11, xmm11->as_VMReg()->next(14));
+reg_def XMM11p( SOC, SOC, Op_RegF, 11, xmm11->as_VMReg()->next(15));
 
 reg_def XMM12 ( SOC, SOC, Op_RegF, 12, xmm12->as_VMReg());
 reg_def XMM12b( SOC, SOC, Op_RegF, 12, xmm12->as_VMReg()->next(1));
@@ -282,6 +733,14 @@
 reg_def XMM12f( SOC, SOC, Op_RegF, 12, xmm12->as_VMReg()->next(5));
 reg_def XMM12g( SOC, SOC, Op_RegF, 12, xmm12->as_VMReg()->next(6));
 reg_def XMM12h( SOC, SOC, Op_RegF, 12, xmm12->as_VMReg()->next(7));
+reg_def XMM12i( SOC, SOC, Op_RegF, 12, xmm12->as_VMReg()->next(8));
+reg_def XMM12j( SOC, SOC, Op_RegF, 12, xmm12->as_VMReg()->next(9));
+reg_def XMM12k( SOC, SOC, Op_RegF, 12, xmm12->as_VMReg()->next(10));
+reg_def XMM12l( SOC, SOC, Op_RegF, 12, xmm12->as_VMReg()->next(11));
+reg_def XMM12m( SOC, SOC, Op_RegF, 12, xmm12->as_VMReg()->next(12));
+reg_def XMM12n( SOC, SOC, Op_RegF, 12, xmm12->as_VMReg()->next(13));
+reg_def XMM12o( SOC, SOC, Op_RegF, 12, xmm12->as_VMReg()->next(14));
+reg_def XMM12p( SOC, SOC, Op_RegF, 12, xmm12->as_VMReg()->next(15));
 
 reg_def XMM13 ( SOC, SOC, Op_RegF, 13, xmm13->as_VMReg());
 reg_def XMM13b( SOC, SOC, Op_RegF, 13, xmm13->as_VMReg()->next(1));
@@ -291,6 +750,14 @@
 reg_def XMM13f( SOC, SOC, Op_RegF, 13, xmm13->as_VMReg()->next(5));
 reg_def XMM13g( SOC, SOC, Op_RegF, 13, xmm13->as_VMReg()->next(6));
 reg_def XMM13h( SOC, SOC, Op_RegF, 13, xmm13->as_VMReg()->next(7));
+reg_def XMM13i( SOC, SOC, Op_RegF, 13, xmm13->as_VMReg()->next(8));
+reg_def XMM13j( SOC, SOC, Op_RegF, 13, xmm13->as_VMReg()->next(9));
+reg_def XMM13k( SOC, SOC, Op_RegF, 13, xmm13->as_VMReg()->next(10));
+reg_def XMM13l( SOC, SOC, Op_RegF, 13, xmm13->as_VMReg()->next(11));
+reg_def XMM13m( SOC, SOC, Op_RegF, 13, xmm13->as_VMReg()->next(12));
+reg_def XMM13n( SOC, SOC, Op_RegF, 13, xmm13->as_VMReg()->next(13));
+reg_def XMM13o( SOC, SOC, Op_RegF, 13, xmm13->as_VMReg()->next(14));
+reg_def XMM13p( SOC, SOC, Op_RegF, 13, xmm13->as_VMReg()->next(15));
 
 reg_def XMM14 ( SOC, SOC, Op_RegF, 14, xmm14->as_VMReg());
 reg_def XMM14b( SOC, SOC, Op_RegF, 14, xmm14->as_VMReg()->next(1));
@@ -300,6 +767,14 @@
 reg_def XMM14f( SOC, SOC, Op_RegF, 14, xmm14->as_VMReg()->next(5));
 reg_def XMM14g( SOC, SOC, Op_RegF, 14, xmm14->as_VMReg()->next(6));
 reg_def XMM14h( SOC, SOC, Op_RegF, 14, xmm14->as_VMReg()->next(7));
+reg_def XMM14i( SOC, SOC, Op_RegF, 14, xmm14->as_VMReg()->next(8));
+reg_def XMM14j( SOC, SOC, Op_RegF, 14, xmm14->as_VMReg()->next(9));
+reg_def XMM14k( SOC, SOC, Op_RegF, 14, xmm14->as_VMReg()->next(10));
+reg_def XMM14l( SOC, SOC, Op_RegF, 14, xmm14->as_VMReg()->next(11));
+reg_def XMM14m( SOC, SOC, Op_RegF, 14, xmm14->as_VMReg()->next(12));
+reg_def XMM14n( SOC, SOC, Op_RegF, 14, xmm14->as_VMReg()->next(13));
+reg_def XMM14o( SOC, SOC, Op_RegF, 14, xmm14->as_VMReg()->next(14));
+reg_def XMM14p( SOC, SOC, Op_RegF, 14, xmm14->as_VMReg()->next(15));
 
 reg_def XMM15 ( SOC, SOC, Op_RegF, 15, xmm15->as_VMReg());
 reg_def XMM15b( SOC, SOC, Op_RegF, 15, xmm15->as_VMReg()->next(1));
@@ -309,6 +784,286 @@
 reg_def XMM15f( SOC, SOC, Op_RegF, 15, xmm15->as_VMReg()->next(5));
 reg_def XMM15g( SOC, SOC, Op_RegF, 15, xmm15->as_VMReg()->next(6));
 reg_def XMM15h( SOC, SOC, Op_RegF, 15, xmm15->as_VMReg()->next(7));
+reg_def XMM15i( SOC, SOC, Op_RegF, 15, xmm15->as_VMReg()->next(8));
+reg_def XMM15j( SOC, SOC, Op_RegF, 15, xmm15->as_VMReg()->next(9));
+reg_def XMM15k( SOC, SOC, Op_RegF, 15, xmm15->as_VMReg()->next(10));
+reg_def XMM15l( SOC, SOC, Op_RegF, 15, xmm15->as_VMReg()->next(11));
+reg_def XMM15m( SOC, SOC, Op_RegF, 15, xmm15->as_VMReg()->next(12));
+reg_def XMM15n( SOC, SOC, Op_RegF, 15, xmm15->as_VMReg()->next(13));
+reg_def XMM15o( SOC, SOC, Op_RegF, 15, xmm15->as_VMReg()->next(14));
+reg_def XMM15p( SOC, SOC, Op_RegF, 15, xmm15->as_VMReg()->next(15));
+
+reg_def XMM16 ( SOC, SOC, Op_RegF, 16, xmm16->as_VMReg());
+reg_def XMM16b( SOC, SOC, Op_RegF, 16, xmm16->as_VMReg()->next(1));
+reg_def XMM16c( SOC, SOC, Op_RegF, 16, xmm16->as_VMReg()->next(2));
+reg_def XMM16d( SOC, SOC, Op_RegF, 16, xmm16->as_VMReg()->next(3));
+reg_def XMM16e( SOC, SOC, Op_RegF, 16, xmm16->as_VMReg()->next(4));
+reg_def XMM16f( SOC, SOC, Op_RegF, 16, xmm16->as_VMReg()->next(5));
+reg_def XMM16g( SOC, SOC, Op_RegF, 16, xmm16->as_VMReg()->next(6));
+reg_def XMM16h( SOC, SOC, Op_RegF, 16, xmm16->as_VMReg()->next(7));
+reg_def XMM16i( SOC, SOC, Op_RegF, 16, xmm16->as_VMReg()->next(8));
+reg_def XMM16j( SOC, SOC, Op_RegF, 16, xmm16->as_VMReg()->next(9));
+reg_def XMM16k( SOC, SOC, Op_RegF, 16, xmm16->as_VMReg()->next(10));
+reg_def XMM16l( SOC, SOC, Op_RegF, 16, xmm16->as_VMReg()->next(11));
+reg_def XMM16m( SOC, SOC, Op_RegF, 16, xmm16->as_VMReg()->next(12));
+reg_def XMM16n( SOC, SOC, Op_RegF, 16, xmm16->as_VMReg()->next(13));
+reg_def XMM16o( SOC, SOC, Op_RegF, 16, xmm16->as_VMReg()->next(14));
+reg_def XMM16p( SOC, SOC, Op_RegF, 16, xmm16->as_VMReg()->next(15));
+
+reg_def XMM17 ( SOC, SOC, Op_RegF, 17, xmm17->as_VMReg());
+reg_def XMM17b( SOC, SOC, Op_RegF, 17, xmm17->as_VMReg()->next(1));
+reg_def XMM17c( SOC, SOC, Op_RegF, 17, xmm17->as_VMReg()->next(2));
+reg_def XMM17d( SOC, SOC, Op_RegF, 17, xmm17->as_VMReg()->next(3));
+reg_def XMM17e( SOC, SOC, Op_RegF, 17, xmm17->as_VMReg()->next(4));
+reg_def XMM17f( SOC, SOC, Op_RegF, 17, xmm17->as_VMReg()->next(5));
+reg_def XMM17g( SOC, SOC, Op_RegF, 17, xmm17->as_VMReg()->next(6));
+reg_def XMM17h( SOC, SOC, Op_RegF, 17, xmm17->as_VMReg()->next(7));
+reg_def XMM17i( SOC, SOC, Op_RegF, 17, xmm17->as_VMReg()->next(8));
+reg_def XMM17j( SOC, SOC, Op_RegF, 17, xmm17->as_VMReg()->next(9));
+reg_def XMM17k( SOC, SOC, Op_RegF, 17, xmm17->as_VMReg()->next(10));
+reg_def XMM17l( SOC, SOC, Op_RegF, 17, xmm17->as_VMReg()->next(11));
+reg_def XMM17m( SOC, SOC, Op_RegF, 17, xmm17->as_VMReg()->next(12));
+reg_def XMM17n( SOC, SOC, Op_RegF, 17, xmm17->as_VMReg()->next(13));
+reg_def XMM17o( SOC, SOC, Op_RegF, 17, xmm17->as_VMReg()->next(14));
+reg_def XMM17p( SOC, SOC, Op_RegF, 17, xmm17->as_VMReg()->next(15));
+
+reg_def XMM18 ( SOC, SOC, Op_RegF, 18, xmm18->as_VMReg());
+reg_def XMM18b( SOC, SOC, Op_RegF, 18, xmm18->as_VMReg()->next(1));
+reg_def XMM18c( SOC, SOC, Op_RegF, 18, xmm18->as_VMReg()->next(2));
+reg_def XMM18d( SOC, SOC, Op_RegF, 18, xmm18->as_VMReg()->next(3));
+reg_def XMM18e( SOC, SOC, Op_RegF, 18, xmm18->as_VMReg()->next(4));
+reg_def XMM18f( SOC, SOC, Op_RegF, 18, xmm18->as_VMReg()->next(5));
+reg_def XMM18g( SOC, SOC, Op_RegF, 18, xmm18->as_VMReg()->next(6));
+reg_def XMM18h( SOC, SOC, Op_RegF, 18, xmm18->as_VMReg()->next(7));
+reg_def XMM18i( SOC, SOC, Op_RegF, 18, xmm18->as_VMReg()->next(8));
+reg_def XMM18j( SOC, SOC, Op_RegF, 18, xmm18->as_VMReg()->next(9));
+reg_def XMM18k( SOC, SOC, Op_RegF, 18, xmm18->as_VMReg()->next(10));
+reg_def XMM18l( SOC, SOC, Op_RegF, 18, xmm18->as_VMReg()->next(11));
+reg_def XMM18m( SOC, SOC, Op_RegF, 18, xmm18->as_VMReg()->next(12));
+reg_def XMM18n( SOC, SOC, Op_RegF, 18, xmm18->as_VMReg()->next(13));
+reg_def XMM18o( SOC, SOC, Op_RegF, 18, xmm18->as_VMReg()->next(14));
+reg_def XMM18p( SOC, SOC, Op_RegF, 18, xmm18->as_VMReg()->next(15));
+
+reg_def XMM19 ( SOC, SOC, Op_RegF, 19, xmm19->as_VMReg());
+reg_def XMM19b( SOC, SOC, Op_RegF, 19, xmm19->as_VMReg()->next(1));
+reg_def XMM19c( SOC, SOC, Op_RegF, 19, xmm19->as_VMReg()->next(2));
+reg_def XMM19d( SOC, SOC, Op_RegF, 19, xmm19->as_VMReg()->next(3));
+reg_def XMM19e( SOC, SOC, Op_RegF, 19, xmm19->as_VMReg()->next(4));
+reg_def XMM19f( SOC, SOC, Op_RegF, 19, xmm19->as_VMReg()->next(5));
+reg_def XMM19g( SOC, SOC, Op_RegF, 19, xmm19->as_VMReg()->next(6));
+reg_def XMM19h( SOC, SOC, Op_RegF, 19, xmm19->as_VMReg()->next(7));
+reg_def XMM19i( SOC, SOC, Op_RegF, 19, xmm19->as_VMReg()->next(8));
+reg_def XMM19j( SOC, SOC, Op_RegF, 19, xmm19->as_VMReg()->next(9));
+reg_def XMM19k( SOC, SOC, Op_RegF, 19, xmm19->as_VMReg()->next(10));
+reg_def XMM19l( SOC, SOC, Op_RegF, 19, xmm19->as_VMReg()->next(11));
+reg_def XMM19m( SOC, SOC, Op_RegF, 19, xmm19->as_VMReg()->next(12));
+reg_def XMM19n( SOC, SOC, Op_RegF, 19, xmm19->as_VMReg()->next(13));
+reg_def XMM19o( SOC, SOC, Op_RegF, 19, xmm19->as_VMReg()->next(14));
+reg_def XMM19p( SOC, SOC, Op_RegF, 19, xmm19->as_VMReg()->next(15));
+
+reg_def XMM20 ( SOC, SOC, Op_RegF, 20, xmm20->as_VMReg());
+reg_def XMM20b( SOC, SOC, Op_RegF, 20, xmm20->as_VMReg()->next(1));
+reg_def XMM20c( SOC, SOC, Op_RegF, 20, xmm20->as_VMReg()->next(2));
+reg_def XMM20d( SOC, SOC, Op_RegF, 20, xmm20->as_VMReg()->next(3));
+reg_def XMM20e( SOC, SOC, Op_RegF, 20, xmm20->as_VMReg()->next(4));
+reg_def XMM20f( SOC, SOC, Op_RegF, 20, xmm20->as_VMReg()->next(5));
+reg_def XMM20g( SOC, SOC, Op_RegF, 20, xmm20->as_VMReg()->next(6));
+reg_def XMM20h( SOC, SOC, Op_RegF, 20, xmm20->as_VMReg()->next(7));
+reg_def XMM20i( SOC, SOC, Op_RegF, 20, xmm20->as_VMReg()->next(8));
+reg_def XMM20j( SOC, SOC, Op_RegF, 20, xmm20->as_VMReg()->next(9));
+reg_def XMM20k( SOC, SOC, Op_RegF, 20, xmm20->as_VMReg()->next(10));
+reg_def XMM20l( SOC, SOC, Op_RegF, 20, xmm20->as_VMReg()->next(11));
+reg_def XMM20m( SOC, SOC, Op_RegF, 20, xmm20->as_VMReg()->next(12));
+reg_def XMM20n( SOC, SOC, Op_RegF, 20, xmm20->as_VMReg()->next(13));
+reg_def XMM20o( SOC, SOC, Op_RegF, 20, xmm20->as_VMReg()->next(14));
+reg_def XMM20p( SOC, SOC, Op_RegF, 20, xmm20->as_VMReg()->next(15));
+
+reg_def XMM21 ( SOC, SOC, Op_RegF, 21, xmm21->as_VMReg());
+reg_def XMM21b( SOC, SOC, Op_RegF, 21, xmm21->as_VMReg()->next(1));
+reg_def XMM21c( SOC, SOC, Op_RegF, 21, xmm21->as_VMReg()->next(2));
+reg_def XMM21d( SOC, SOC, Op_RegF, 21, xmm21->as_VMReg()->next(3));
+reg_def XMM21e( SOC, SOC, Op_RegF, 21, xmm21->as_VMReg()->next(4));
+reg_def XMM21f( SOC, SOC, Op_RegF, 21, xmm21->as_VMReg()->next(5));
+reg_def XMM21g( SOC, SOC, Op_RegF, 21, xmm21->as_VMReg()->next(6));
+reg_def XMM21h( SOC, SOC, Op_RegF, 21, xmm21->as_VMReg()->next(7));
+reg_def XMM21i( SOC, SOC, Op_RegF, 21, xmm21->as_VMReg()->next(8));
+reg_def XMM21j( SOC, SOC, Op_RegF, 21, xmm21->as_VMReg()->next(9));
+reg_def XMM21k( SOC, SOC, Op_RegF, 21, xmm21->as_VMReg()->next(10));
+reg_def XMM21l( SOC, SOC, Op_RegF, 21, xmm21->as_VMReg()->next(11));
+reg_def XMM21m( SOC, SOC, Op_RegF, 21, xmm21->as_VMReg()->next(12));
+reg_def XMM21n( SOC, SOC, Op_RegF, 21, xmm21->as_VMReg()->next(13));
+reg_def XMM21o( SOC, SOC, Op_RegF, 21, xmm21->as_VMReg()->next(14));
+reg_def XMM21p( SOC, SOC, Op_RegF, 21, xmm21->as_VMReg()->next(15));
+
+reg_def XMM22 ( SOC, SOC, Op_RegF, 22, xmm22->as_VMReg());
+reg_def XMM22b( SOC, SOC, Op_RegF, 22, xmm22->as_VMReg()->next(1));
+reg_def XMM22c( SOC, SOC, Op_RegF, 22, xmm22->as_VMReg()->next(2));
+reg_def XMM22d( SOC, SOC, Op_RegF, 22, xmm22->as_VMReg()->next(3));
+reg_def XMM22e( SOC, SOC, Op_RegF, 22, xmm22->as_VMReg()->next(4));
+reg_def XMM22f( SOC, SOC, Op_RegF, 22, xmm22->as_VMReg()->next(5));
+reg_def XMM22g( SOC, SOC, Op_RegF, 22, xmm22->as_VMReg()->next(6));
+reg_def XMM22h( SOC, SOC, Op_RegF, 22, xmm22->as_VMReg()->next(7));
+reg_def XMM22i( SOC, SOC, Op_RegF, 22, xmm22->as_VMReg()->next(8));
+reg_def XMM22j( SOC, SOC, Op_RegF, 22, xmm22->as_VMReg()->next(9));
+reg_def XMM22k( SOC, SOC, Op_RegF, 22, xmm22->as_VMReg()->next(10));
+reg_def XMM22l( SOC, SOC, Op_RegF, 22, xmm22->as_VMReg()->next(11));
+reg_def XMM22m( SOC, SOC, Op_RegF, 22, xmm22->as_VMReg()->next(12));
+reg_def XMM22n( SOC, SOC, Op_RegF, 22, xmm22->as_VMReg()->next(13));
+reg_def XMM22o( SOC, SOC, Op_RegF, 22, xmm22->as_VMReg()->next(14));
+reg_def XMM22p( SOC, SOC, Op_RegF, 22, xmm22->as_VMReg()->next(15));
+
+reg_def XMM23 ( SOC, SOC, Op_RegF, 23, xmm23->as_VMReg());
+reg_def XMM23b( SOC, SOC, Op_RegF, 23, xmm23->as_VMReg()->next(1));
+reg_def XMM23c( SOC, SOC, Op_RegF, 23, xmm23->as_VMReg()->next(2));
+reg_def XMM23d( SOC, SOC, Op_RegF, 23, xmm23->as_VMReg()->next(3));
+reg_def XMM23e( SOC, SOC, Op_RegF, 23, xmm23->as_VMReg()->next(4));
+reg_def XMM23f( SOC, SOC, Op_RegF, 23, xmm23->as_VMReg()->next(5));
+reg_def XMM23g( SOC, SOC, Op_RegF, 23, xmm23->as_VMReg()->next(6));
+reg_def XMM23h( SOC, SOC, Op_RegF, 23, xmm23->as_VMReg()->next(7));
+reg_def XMM23i( SOC, SOC, Op_RegF, 23, xmm23->as_VMReg()->next(8));
+reg_def XMM23j( SOC, SOC, Op_RegF, 23, xmm23->as_VMReg()->next(9));
+reg_def XMM23k( SOC, SOC, Op_RegF, 23, xmm23->as_VMReg()->next(10));
+reg_def XMM23l( SOC, SOC, Op_RegF, 23, xmm23->as_VMReg()->next(11));
+reg_def XMM23m( SOC, SOC, Op_RegF, 23, xmm23->as_VMReg()->next(12));
+reg_def XMM23n( SOC, SOC, Op_RegF, 23, xmm23->as_VMReg()->next(13));
+reg_def XMM23o( SOC, SOC, Op_RegF, 23, xmm23->as_VMReg()->next(14));
+reg_def XMM23p( SOC, SOC, Op_RegF, 23, xmm23->as_VMReg()->next(15));
+
+reg_def XMM24 ( SOC, SOC, Op_RegF, 24, xmm24->as_VMReg());
+reg_def XMM24b( SOC, SOC, Op_RegF, 24, xmm24->as_VMReg()->next(1));
+reg_def XMM24c( SOC, SOC, Op_RegF, 24, xmm24->as_VMReg()->next(2));
+reg_def XMM24d( SOC, SOC, Op_RegF, 24, xmm24->as_VMReg()->next(3));
+reg_def XMM24e( SOC, SOC, Op_RegF, 24, xmm24->as_VMReg()->next(4));
+reg_def XMM24f( SOC, SOC, Op_RegF, 24, xmm24->as_VMReg()->next(5));
+reg_def XMM24g( SOC, SOC, Op_RegF, 24, xmm24->as_VMReg()->next(6));
+reg_def XMM24h( SOC, SOC, Op_RegF, 24, xmm24->as_VMReg()->next(7));
+reg_def XMM24i( SOC, SOC, Op_RegF, 24, xmm24->as_VMReg()->next(8));
+reg_def XMM24j( SOC, SOC, Op_RegF, 24, xmm24->as_VMReg()->next(9));
+reg_def XMM24k( SOC, SOC, Op_RegF, 24, xmm24->as_VMReg()->next(10));
+reg_def XMM24l( SOC, SOC, Op_RegF, 24, xmm24->as_VMReg()->next(11));
+reg_def XMM24m( SOC, SOC, Op_RegF, 24, xmm24->as_VMReg()->next(12));
+reg_def XMM24n( SOC, SOC, Op_RegF, 24, xmm24->as_VMReg()->next(13));
+reg_def XMM24o( SOC, SOC, Op_RegF, 24, xmm24->as_VMReg()->next(14));
+reg_def XMM24p( SOC, SOC, Op_RegF, 24, xmm24->as_VMReg()->next(15));
+
+reg_def XMM25 ( SOC, SOC, Op_RegF, 25, xmm25->as_VMReg());
+reg_def XMM25b( SOC, SOC, Op_RegF, 25, xmm25->as_VMReg()->next(1));
+reg_def XMM25c( SOC, SOC, Op_RegF, 25, xmm25->as_VMReg()->next(2));
+reg_def XMM25d( SOC, SOC, Op_RegF, 25, xmm25->as_VMReg()->next(3));
+reg_def XMM25e( SOC, SOC, Op_RegF, 25, xmm25->as_VMReg()->next(4));
+reg_def XMM25f( SOC, SOC, Op_RegF, 25, xmm25->as_VMReg()->next(5));
+reg_def XMM25g( SOC, SOC, Op_RegF, 25, xmm25->as_VMReg()->next(6));
+reg_def XMM25h( SOC, SOC, Op_RegF, 25, xmm25->as_VMReg()->next(7));
+reg_def XMM25i( SOC, SOC, Op_RegF, 25, xmm25->as_VMReg()->next(8));
+reg_def XMM25j( SOC, SOC, Op_RegF, 25, xmm25->as_VMReg()->next(9));
+reg_def XMM25k( SOC, SOC, Op_RegF, 25, xmm25->as_VMReg()->next(10));
+reg_def XMM25l( SOC, SOC, Op_RegF, 25, xmm25->as_VMReg()->next(11));
+reg_def XMM25m( SOC, SOC, Op_RegF, 25, xmm25->as_VMReg()->next(12));
+reg_def XMM25n( SOC, SOC, Op_RegF, 25, xmm25->as_VMReg()->next(13));
+reg_def XMM25o( SOC, SOC, Op_RegF, 25, xmm25->as_VMReg()->next(14));
+reg_def XMM25p( SOC, SOC, Op_RegF, 25, xmm25->as_VMReg()->next(15));
+
+reg_def XMM26 ( SOC, SOC, Op_RegF, 26, xmm26->as_VMReg());
+reg_def XMM26b( SOC, SOC, Op_RegF, 26, xmm26->as_VMReg()->next(1));
+reg_def XMM26c( SOC, SOC, Op_RegF, 26, xmm26->as_VMReg()->next(2));
+reg_def XMM26d( SOC, SOC, Op_RegF, 26, xmm26->as_VMReg()->next(3));
+reg_def XMM26e( SOC, SOC, Op_RegF, 26, xmm26->as_VMReg()->next(4));
+reg_def XMM26f( SOC, SOC, Op_RegF, 26, xmm26->as_VMReg()->next(5));
+reg_def XMM26g( SOC, SOC, Op_RegF, 26, xmm26->as_VMReg()->next(6));
+reg_def XMM26h( SOC, SOC, Op_RegF, 26, xmm26->as_VMReg()->next(7));
+reg_def XMM26i( SOC, SOC, Op_RegF, 26, xmm26->as_VMReg()->next(8));
+reg_def XMM26j( SOC, SOC, Op_RegF, 26, xmm26->as_VMReg()->next(9));
+reg_def XMM26k( SOC, SOC, Op_RegF, 26, xmm26->as_VMReg()->next(10));
+reg_def XMM26l( SOC, SOC, Op_RegF, 26, xmm26->as_VMReg()->next(11));
+reg_def XMM26m( SOC, SOC, Op_RegF, 26, xmm26->as_VMReg()->next(12));
+reg_def XMM26n( SOC, SOC, Op_RegF, 26, xmm26->as_VMReg()->next(13));
+reg_def XMM26o( SOC, SOC, Op_RegF, 26, xmm26->as_VMReg()->next(14));
+reg_def XMM26p( SOC, SOC, Op_RegF, 26, xmm26->as_VMReg()->next(15));
+
+reg_def XMM27 ( SOC, SOC, Op_RegF, 27, xmm27->as_VMReg());
+reg_def XMM27b( SOC, SOC, Op_RegF, 27, xmm27->as_VMReg()->next(1));
+reg_def XMM27c( SOC, SOC, Op_RegF, 27, xmm27->as_VMReg()->next(2));
+reg_def XMM27d( SOC, SOC, Op_RegF, 27, xmm27->as_VMReg()->next(3));
+reg_def XMM27e( SOC, SOC, Op_RegF, 27, xmm27->as_VMReg()->next(4));
+reg_def XMM27f( SOC, SOC, Op_RegF, 27, xmm27->as_VMReg()->next(5));
+reg_def XMM27g( SOC, SOC, Op_RegF, 27, xmm27->as_VMReg()->next(6));
+reg_def XMM27h( SOC, SOC, Op_RegF, 27, xmm27->as_VMReg()->next(7));
+reg_def XMM27i( SOC, SOC, Op_RegF, 27, xmm27->as_VMReg()->next(8));
+reg_def XMM27j( SOC, SOC, Op_RegF, 27, xmm27->as_VMReg()->next(9));
+reg_def XMM27k( SOC, SOC, Op_RegF, 27, xmm27->as_VMReg()->next(10));
+reg_def XMM27l( SOC, SOC, Op_RegF, 27, xmm27->as_VMReg()->next(11));
+reg_def XMM27m( SOC, SOC, Op_RegF, 27, xmm27->as_VMReg()->next(12));
+reg_def XMM27n( SOC, SOC, Op_RegF, 27, xmm27->as_VMReg()->next(13));
+reg_def XMM27o( SOC, SOC, Op_RegF, 27, xmm27->as_VMReg()->next(14));
+reg_def XMM27p( SOC, SOC, Op_RegF, 27, xmm27->as_VMReg()->next(15));
+
+reg_def XMM28 ( SOC, SOC, Op_RegF, 28, xmm28->as_VMReg());
+reg_def XMM28b( SOC, SOC, Op_RegF, 28, xmm28->as_VMReg()->next(1));
+reg_def XMM28c( SOC, SOC, Op_RegF, 28, xmm28->as_VMReg()->next(2));
+reg_def XMM28d( SOC, SOC, Op_RegF, 28, xmm28->as_VMReg()->next(3));
+reg_def XMM28e( SOC, SOC, Op_RegF, 28, xmm28->as_VMReg()->next(4));
+reg_def XMM28f( SOC, SOC, Op_RegF, 28, xmm28->as_VMReg()->next(5));
+reg_def XMM28g( SOC, SOC, Op_RegF, 28, xmm28->as_VMReg()->next(6));
+reg_def XMM28h( SOC, SOC, Op_RegF, 28, xmm28->as_VMReg()->next(7));
+reg_def XMM28i( SOC, SOC, Op_RegF, 28, xmm28->as_VMReg()->next(8));
+reg_def XMM28j( SOC, SOC, Op_RegF, 28, xmm28->as_VMReg()->next(9));
+reg_def XMM28k( SOC, SOC, Op_RegF, 28, xmm28->as_VMReg()->next(10));
+reg_def XMM28l( SOC, SOC, Op_RegF, 28, xmm28->as_VMReg()->next(11));
+reg_def XMM28m( SOC, SOC, Op_RegF, 28, xmm28->as_VMReg()->next(12));
+reg_def XMM28n( SOC, SOC, Op_RegF, 28, xmm28->as_VMReg()->next(13));
+reg_def XMM28o( SOC, SOC, Op_RegF, 28, xmm28->as_VMReg()->next(14));
+reg_def XMM28p( SOC, SOC, Op_RegF, 28, xmm28->as_VMReg()->next(15));
+
+reg_def XMM29 ( SOC, SOC, Op_RegF, 29, xmm29->as_VMReg());
+reg_def XMM29b( SOC, SOC, Op_RegF, 29, xmm29->as_VMReg()->next(1));
+reg_def XMM29c( SOC, SOC, Op_RegF, 29, xmm29->as_VMReg()->next(2));
+reg_def XMM29d( SOC, SOC, Op_RegF, 29, xmm29->as_VMReg()->next(3));
+reg_def XMM29e( SOC, SOC, Op_RegF, 29, xmm29->as_VMReg()->next(4));
+reg_def XMM29f( SOC, SOC, Op_RegF, 29, xmm29->as_VMReg()->next(5));
+reg_def XMM29g( SOC, SOC, Op_RegF, 29, xmm29->as_VMReg()->next(6));
+reg_def XMM29h( SOC, SOC, Op_RegF, 29, xmm29->as_VMReg()->next(7));
+reg_def XMM29i( SOC, SOC, Op_RegF, 29, xmm29->as_VMReg()->next(8));
+reg_def XMM29j( SOC, SOC, Op_RegF, 29, xmm29->as_VMReg()->next(9));
+reg_def XMM29k( SOC, SOC, Op_RegF, 29, xmm29->as_VMReg()->next(10));
+reg_def XMM29l( SOC, SOC, Op_RegF, 29, xmm29->as_VMReg()->next(11));
+reg_def XMM29m( SOC, SOC, Op_RegF, 29, xmm29->as_VMReg()->next(12));
+reg_def XMM29n( SOC, SOC, Op_RegF, 29, xmm29->as_VMReg()->next(13));
+reg_def XMM29o( SOC, SOC, Op_RegF, 29, xmm29->as_VMReg()->next(14));
+reg_def XMM29p( SOC, SOC, Op_RegF, 29, xmm29->as_VMReg()->next(15));
+
+reg_def XMM30 ( SOC, SOC, Op_RegF, 30, xmm30->as_VMReg());
+reg_def XMM30b( SOC, SOC, Op_RegF, 30, xmm30->as_VMReg()->next(1));
+reg_def XMM30c( SOC, SOC, Op_RegF, 30, xmm30->as_VMReg()->next(2));
+reg_def XMM30d( SOC, SOC, Op_RegF, 30, xmm30->as_VMReg()->next(3));
+reg_def XMM30e( SOC, SOC, Op_RegF, 30, xmm30->as_VMReg()->next(4));
+reg_def XMM30f( SOC, SOC, Op_RegF, 30, xmm30->as_VMReg()->next(5));
+reg_def XMM30g( SOC, SOC, Op_RegF, 30, xmm30->as_VMReg()->next(6));
+reg_def XMM30h( SOC, SOC, Op_RegF, 30, xmm30->as_VMReg()->next(7));
+reg_def XMM30i( SOC, SOC, Op_RegF, 30, xmm30->as_VMReg()->next(8));
+reg_def XMM30j( SOC, SOC, Op_RegF, 30, xmm30->as_VMReg()->next(9));
+reg_def XMM30k( SOC, SOC, Op_RegF, 30, xmm30->as_VMReg()->next(10));
+reg_def XMM30l( SOC, SOC, Op_RegF, 30, xmm30->as_VMReg()->next(11));
+reg_def XMM30m( SOC, SOC, Op_RegF, 30, xmm30->as_VMReg()->next(12));
+reg_def XMM30n( SOC, SOC, Op_RegF, 30, xmm30->as_VMReg()->next(13));
+reg_def XMM30o( SOC, SOC, Op_RegF, 30, xmm30->as_VMReg()->next(14));
+reg_def XMM30p( SOC, SOC, Op_RegF, 30, xmm30->as_VMReg()->next(15));
+
+reg_def XMM31 ( SOC, SOC, Op_RegF, 31, xmm31->as_VMReg());
+reg_def XMM31b( SOC, SOC, Op_RegF, 31, xmm31->as_VMReg()->next(1));
+reg_def XMM31c( SOC, SOC, Op_RegF, 31, xmm31->as_VMReg()->next(2));
+reg_def XMM31d( SOC, SOC, Op_RegF, 31, xmm31->as_VMReg()->next(3));
+reg_def XMM31e( SOC, SOC, Op_RegF, 31, xmm31->as_VMReg()->next(4));
+reg_def XMM31f( SOC, SOC, Op_RegF, 31, xmm31->as_VMReg()->next(5));
+reg_def XMM31g( SOC, SOC, Op_RegF, 31, xmm31->as_VMReg()->next(6));
+reg_def XMM31h( SOC, SOC, Op_RegF, 31, xmm31->as_VMReg()->next(7));
+reg_def XMM31i( SOC, SOC, Op_RegF, 31, xmm31->as_VMReg()->next(8));
+reg_def XMM31j( SOC, SOC, Op_RegF, 31, xmm31->as_VMReg()->next(9));
+reg_def XMM31k( SOC, SOC, Op_RegF, 31, xmm31->as_VMReg()->next(10));
+reg_def XMM31l( SOC, SOC, Op_RegF, 31, xmm31->as_VMReg()->next(11));
+reg_def XMM31m( SOC, SOC, Op_RegF, 31, xmm31->as_VMReg()->next(12));
+reg_def XMM31n( SOC, SOC, Op_RegF, 31, xmm31->as_VMReg()->next(13));
+reg_def XMM31o( SOC, SOC, Op_RegF, 31, xmm31->as_VMReg()->next(14));
+reg_def XMM31p( SOC, SOC, Op_RegF, 31, xmm31->as_VMReg()->next(15));
 
 #endif // _LP64
 
@@ -320,25 +1075,41 @@
 reg_def RFLAGS(SOC, SOC, 0, 8, VMRegImpl::Bad());
 #endif // _LP64
 
-alloc_class chunk1(XMM0,  XMM0b,  XMM0c,  XMM0d,  XMM0e,  XMM0f,  XMM0g,  XMM0h,
-                   XMM1,  XMM1b,  XMM1c,  XMM1d,  XMM1e,  XMM1f,  XMM1g,  XMM1h,
-                   XMM2,  XMM2b,  XMM2c,  XMM2d,  XMM2e,  XMM2f,  XMM2g,  XMM2h,
-                   XMM3,  XMM3b,  XMM3c,  XMM3d,  XMM3e,  XMM3f,  XMM3g,  XMM3h,
-                   XMM4,  XMM4b,  XMM4c,  XMM4d,  XMM4e,  XMM4f,  XMM4g,  XMM4h,
-                   XMM5,  XMM5b,  XMM5c,  XMM5d,  XMM5e,  XMM5f,  XMM5g,  XMM5h,
-                   XMM6,  XMM6b,  XMM6c,  XMM6d,  XMM6e,  XMM6f,  XMM6g,  XMM6h,
-                   XMM7,  XMM7b,  XMM7c,  XMM7d,  XMM7e,  XMM7f,  XMM7g,  XMM7h
+alloc_class chunk1(XMM0,  XMM0b,  XMM0c,  XMM0d,  XMM0e,  XMM0f,  XMM0g,  XMM0h,  XMM0i,  XMM0j,  XMM0k,  XMM0l,  XMM0m,  XMM0n,  XMM0o,  XMM0p,
+                   XMM1,  XMM1b,  XMM1c,  XMM1d,  XMM1e,  XMM1f,  XMM1g,  XMM1h,  XMM1i,  XMM1j,  XMM1k,  XMM1l,  XMM1m,  XMM1n,  XMM1o,  XMM1p,
+                   XMM2,  XMM2b,  XMM2c,  XMM2d,  XMM2e,  XMM2f,  XMM2g,  XMM2h,  XMM2i,  XMM2j,  XMM2k,  XMM2l,  XMM2m,  XMM2n,  XMM2o,  XMM2p,
+                   XMM3,  XMM3b,  XMM3c,  XMM3d,  XMM3e,  XMM3f,  XMM3g,  XMM3h,  XMM3i,  XMM3j,  XMM3k,  XMM3l,  XMM3m,  XMM3n,  XMM3o,  XMM3p,
+                   XMM4,  XMM4b,  XMM4c,  XMM4d,  XMM4e,  XMM4f,  XMM4g,  XMM4h,  XMM4i,  XMM4j,  XMM4k,  XMM4l,  XMM4m,  XMM4n,  XMM4o,  XMM4p,
+                   XMM5,  XMM5b,  XMM5c,  XMM5d,  XMM5e,  XMM5f,  XMM5g,  XMM5h,  XMM5i,  XMM5j,  XMM5k,  XMM5l,  XMM5m,  XMM5n,  XMM5o,  XMM5p,
+                   XMM6,  XMM6b,  XMM6c,  XMM6d,  XMM6e,  XMM6f,  XMM6g,  XMM6h,  XMM6i,  XMM6j,  XMM6k,  XMM6l,  XMM6m,  XMM6n,  XMM6o,  XMM6p,
+                   XMM7,  XMM7b,  XMM7c,  XMM7d,  XMM7e,  XMM7f,  XMM7g,  XMM7h,  XMM7i,  XMM7j,  XMM7k,  XMM7l,  XMM7m,  XMM7n,  XMM7o,  XMM7p
 #ifdef _LP64
-                  ,XMM8,  XMM8b,  XMM8c,  XMM8d,  XMM8e,  XMM8f,  XMM8g,  XMM8h,
-                   XMM9,  XMM9b,  XMM9c,  XMM9d,  XMM9e,  XMM9f,  XMM9g,  XMM9h,
-                   XMM10, XMM10b, XMM10c, XMM10d, XMM10e, XMM10f, XMM10g, XMM10h,
-                   XMM11, XMM11b, XMM11c, XMM11d, XMM11e, XMM11f, XMM11g, XMM11h,
-                   XMM12, XMM12b, XMM12c, XMM12d, XMM12e, XMM12f, XMM12g, XMM12h,
-                   XMM13, XMM13b, XMM13c, XMM13d, XMM13e, XMM13f, XMM13g, XMM13h,
-                   XMM14, XMM14b, XMM14c, XMM14d, XMM14e, XMM14f, XMM14g, XMM14h,
-                   XMM15, XMM15b, XMM15c, XMM15d, XMM15e, XMM15f, XMM15g, XMM15h
+                  ,XMM8,  XMM8b,  XMM8c,  XMM8d,  XMM8e,  XMM8f,  XMM8g,  XMM8h,  XMM8i,  XMM8j,  XMM8k,  XMM8l,  XMM8m,  XMM8n,  XMM8o,  XMM8p,
+                   XMM9,  XMM9b,  XMM9c,  XMM9d,  XMM9e,  XMM9f,  XMM9g,  XMM9h,  XMM9i,  XMM9j,  XMM9k,  XMM9l,  XMM9m,  XMM9n,  XMM9o,  XMM9p,
+                   XMM10, XMM10b, XMM10c, XMM10d, XMM10e, XMM10f, XMM10g, XMM10h, XMM10i, XMM10j, XMM10k, XMM10l, XMM10m, XMM10n, XMM10o, XMM10p,
+                   XMM11, XMM11b, XMM11c, XMM11d, XMM11e, XMM11f, XMM11g, XMM11h, XMM11i, XMM11j, XMM11k, XMM11l, XMM11m, XMM11n, XMM11o, XMM11p,
+                   XMM12, XMM12b, XMM12c, XMM12d, XMM12e, XMM12f, XMM12g, XMM12h, XMM12i, XMM12j, XMM12k, XMM12l, XMM12m, XMM12n, XMM12o, XMM12p,
+                   XMM13, XMM13b, XMM13c, XMM13d, XMM13e, XMM13f, XMM13g, XMM13h, XMM13i, XMM13j, XMM13k, XMM13l, XMM13m, XMM13n, XMM13o, XMM13p,
+                   XMM14, XMM14b, XMM14c, XMM14d, XMM14e, XMM14f, XMM14g, XMM14h, XMM14i, XMM14j, XMM14k, XMM14l, XMM14m, XMM14n, XMM14o, XMM14p,
+                   XMM15, XMM15b, XMM15c, XMM15d, XMM15e, XMM15f, XMM15g, XMM15h, XMM15i, XMM15j, XMM15k, XMM15l, XMM15m, XMM15n, XMM15o, XMM15p
+                  ,XMM16, XMM16b, XMM16c, XMM16d, XMM16e, XMM16f, XMM16g, XMM16h, XMM16i, XMM16j, XMM16k, XMM16l, XMM16m, XMM16n, XMM16o, XMM16p,
+                   XMM17, XMM17b, XMM17c, XMM17d, XMM17e, XMM17f, XMM17g, XMM17h, XMM17i, XMM17j, XMM17k, XMM17l, XMM17m, XMM17n, XMM17o, XMM17p,
+                   XMM18, XMM18b, XMM18c, XMM18d, XMM18e, XMM18f, XMM18g, XMM18h, XMM18i, XMM18j, XMM18k, XMM18l, XMM18m, XMM18n, XMM18o, XMM18p,
+                   XMM19, XMM19b, XMM19c, XMM19d, XMM19e, XMM19f, XMM19g, XMM19h, XMM19i, XMM19j, XMM19k, XMM19l, XMM19m, XMM19n, XMM19o, XMM19p,
+                   XMM20, XMM20b, XMM20c, XMM20d, XMM20e, XMM20f, XMM20g, XMM20h, XMM20i, XMM20j, XMM20k, XMM20l, XMM20m, XMM20n, XMM20o, XMM20p,
+                   XMM21, XMM21b, XMM21c, XMM21d, XMM21e, XMM21f, XMM21g, XMM21h, XMM21i, XMM21j, XMM21k, XMM21l, XMM21m, XMM21n, XMM21o, XMM21p,
+                   XMM22, XMM22b, XMM22c, XMM22d, XMM22e, XMM22f, XMM22g, XMM22h, XMM22i, XMM22j, XMM22k, XMM22l, XMM22m, XMM22n, XMM22o, XMM22p,
+                   XMM23, XMM23b, XMM23c, XMM23d, XMM23e, XMM23f, XMM23g, XMM23h, XMM23i, XMM23j, XMM23k, XMM23l, XMM23m, XMM23n, XMM23o, XMM23p,
+                   XMM24, XMM24b, XMM24c, XMM24d, XMM24e, XMM24f, XMM24g, XMM24h, XMM24i, XMM24j, XMM24k, XMM24l, XMM24m, XMM24n, XMM24o, XMM24p,
+                   XMM25, XMM25b, XMM25c, XMM25d, XMM25e, XMM25f, XMM25g, XMM25h, XMM25i, XMM25j, XMM25k, XMM25l, XMM25m, XMM25n, XMM25o, XMM25p,
+                   XMM26, XMM26b, XMM26c, XMM26d, XMM26e, XMM26f, XMM26g, XMM26h, XMM26i, XMM26j, XMM26k, XMM26l, XMM26m, XMM26n, XMM26o, XMM26p,
+                   XMM27, XMM27b, XMM27c, XMM27d, XMM27e, XMM27f, XMM27g, XMM27h, XMM27i, XMM27j, XMM27k, XMM27l, XMM27m, XMM27n, XMM27o, XMM27p,
+                   XMM28, XMM28b, XMM28c, XMM28d, XMM28e, XMM28f, XMM28g, XMM28h, XMM28i, XMM28j, XMM28k, XMM28l, XMM28m, XMM28n, XMM28o, XMM28p,
+                   XMM29, XMM29b, XMM29c, XMM29d, XMM29e, XMM29f, XMM29g, XMM29h, XMM29i, XMM29j, XMM29k, XMM29l, XMM29m, XMM29n, XMM29o, XMM29p,
+                   XMM30, XMM30b, XMM30c, XMM30d, XMM30e, XMM30f, XMM30g, XMM30h, XMM30i, XMM30j, XMM30k, XMM30l, XMM30m, XMM30n, XMM30o, XMM30p,
+                   XMM31, XMM31b, XMM31c, XMM31d, XMM31e, XMM31f, XMM31g, XMM31h, XMM31i, XMM31j, XMM31k, XMM31l, XMM31m, XMM31n, XMM31o, XMM31p
 #endif
-                   );
+                      );
 
 // flags allocation class should be last.
 alloc_class chunk2(RFLAGS);
@@ -346,8 +1117,8 @@
 // Singleton class for condition codes
 reg_class int_flags(RFLAGS);
 
-// Class for all float registers
-reg_class float_reg(XMM0,
+// Class for pre evex float registers
+reg_class float_reg_legacy(XMM0,
                     XMM1,
                     XMM2,
                     XMM3,
@@ -367,8 +1138,47 @@
 #endif
                     );
 
-// Class for all double registers
-reg_class double_reg(XMM0,  XMM0b,
+// Class for evex float registers
+reg_class float_reg_evex(XMM0,
+                    XMM1,
+                    XMM2,
+                    XMM3,
+                    XMM4,
+                    XMM5,
+                    XMM6,
+                    XMM7
+#ifdef _LP64
+                   ,XMM8,
+                    XMM9,
+                    XMM10,
+                    XMM11,
+                    XMM12,
+                    XMM13,
+                    XMM14,
+                    XMM15,
+                    XMM16,
+                    XMM17,
+                    XMM18,
+                    XMM19,
+                    XMM20,
+                    XMM21,
+                    XMM22,
+                    XMM23,
+                    XMM24,
+                    XMM25,
+                    XMM26,
+                    XMM27,
+                    XMM28,
+                    XMM29,
+                    XMM30,
+                    XMM31
+#endif
+                    );
+
+reg_class_dynamic float_reg(float_reg_evex, float_reg_legacy, %{ VM_Version::supports_evex() %} );
+
+// Class for pre evex double registers
+reg_class double_reg_legacy(XMM0,  XMM0b,
                      XMM1,  XMM1b,
                      XMM2,  XMM2b,
                      XMM3,  XMM3b,
@@ -388,8 +1198,47 @@
 #endif
                      );
 
-// Class for all 32bit vector registers
-reg_class vectors_reg(XMM0,
+// Class for evex double registers
+reg_class double_reg_evex(XMM0,  XMM0b,
+                     XMM1,  XMM1b,
+                     XMM2,  XMM2b,
+                     XMM3,  XMM3b,
+                     XMM4,  XMM4b,
+                     XMM5,  XMM5b,
+                     XMM6,  XMM6b,
+                     XMM7,  XMM7b
+#ifdef _LP64
+                    ,XMM8,  XMM8b,
+                     XMM9,  XMM9b,
+                     XMM10, XMM10b,
+                     XMM11, XMM11b,
+                     XMM12, XMM12b,
+                     XMM13, XMM13b,
+                     XMM14, XMM14b,
+                     XMM15, XMM15b,
+                     XMM16, XMM16b,
+                     XMM17, XMM17b,
+                     XMM18, XMM18b,
+                     XMM19, XMM19b,
+                     XMM20, XMM20b,
+                     XMM21, XMM21b,
+                     XMM22, XMM22b,
+                     XMM23, XMM23b,
+                     XMM24, XMM24b,
+                     XMM25, XMM25b,
+                     XMM26, XMM26b,
+                     XMM27, XMM27b,
+                     XMM28, XMM28b,
+                     XMM29, XMM29b,
+                     XMM30, XMM30b,
+                     XMM31, XMM31b
+#endif
+                     );
+
+reg_class_dynamic double_reg(double_reg_evex, double_reg_legacy, %{ VM_Version::supports_evex() %} );
+
+// Class for pre evex 32bit vector registers
+reg_class vectors_reg_legacy(XMM0,
                       XMM1,
                       XMM2,
                       XMM3,
@@ -409,8 +1258,47 @@
 #endif
                       );
 
+// Class for evex 32bit vector registers
+reg_class vectors_reg_evex(XMM0,
+                      XMM1,
+                      XMM2,
+                      XMM3,
+                      XMM4,
+                      XMM5,
+                      XMM6,
+                      XMM7
+#ifdef _LP64
+                     ,XMM8,
+                      XMM9,
+                      XMM10,
+                      XMM11,
+                      XMM12,
+                      XMM13,
+                      XMM14,
+                      XMM15,
+                      XMM16,
+                      XMM17,
+                      XMM18,
+                      XMM19,
+                      XMM20,
+                      XMM21,
+                      XMM22,
+                      XMM23,
+                      XMM24,
+                      XMM25,
+                      XMM26,
+                      XMM27,
+                      XMM28,
+                      XMM29,
+                      XMM30,
+                      XMM31
+#endif
+                      );
+
+reg_class_dynamic vectors_reg(vectors_reg_evex, vectors_reg_legacy, %{ VM_Version::supports_evex() %} );
+
 // Class for all 64bit vector registers
-reg_class vectord_reg(XMM0,  XMM0b,
+reg_class vectord_reg_legacy(XMM0,  XMM0b,
                       XMM1,  XMM1b,
                       XMM2,  XMM2b,
                       XMM3,  XMM3b,
@@ -430,8 +1318,47 @@
 #endif
                       );
 
+// Class for all 64bit vector registers
+reg_class vectord_reg_evex(XMM0,  XMM0b,
+                      XMM1,  XMM1b,
+                      XMM2,  XMM2b,
+                      XMM3,  XMM3b,
+                      XMM4,  XMM4b,
+                      XMM5,  XMM5b,
+                      XMM6,  XMM6b,
+                      XMM7,  XMM7b
+#ifdef _LP64
+                     ,XMM8,  XMM8b,
+                      XMM9,  XMM9b,
+                      XMM10, XMM10b,
+                      XMM11, XMM11b,
+                      XMM12, XMM12b,
+                      XMM13, XMM13b,
+                      XMM14, XMM14b,
+                      XMM15, XMM15b,
+                      XMM16, XMM16b,
+                      XMM17, XMM17b,
+                      XMM18, XMM18b,
+                      XMM19, XMM19b,
+                      XMM20, XMM20b,
+                      XMM21, XMM21b,
+                      XMM22, XMM22b,
+                      XMM23, XMM23b,
+                      XMM24, XMM24b,
+                      XMM25, XMM25b,
+                      XMM26, XMM26b,
+                      XMM27, XMM27b,
+                      XMM28, XMM28b,
+                      XMM29, XMM29b,
+                      XMM30, XMM30b,
+                      XMM31, XMM31b
+#endif
+                      );
+
+reg_class_dynamic vectord_reg(vectord_reg_evex, vectord_reg_legacy, %{ VM_Version::supports_evex() %} );
+
 // Class for all 128bit vector registers
-reg_class vectorx_reg(XMM0,  XMM0b,  XMM0c,  XMM0d,
+reg_class vectorx_reg_legacy(XMM0,  XMM0b,  XMM0c,  XMM0d,
                       XMM1,  XMM1b,  XMM1c,  XMM1d,
                       XMM2,  XMM2b,  XMM2c,  XMM2d,
                       XMM3,  XMM3b,  XMM3c,  XMM3d,
@@ -451,8 +1378,47 @@
 #endif
                       );
 
+// Class for all 128bit vector registers
+reg_class vectorx_reg_evex(XMM0,  XMM0b,  XMM0c,  XMM0d,
+                      XMM1,  XMM1b,  XMM1c,  XMM1d,
+                      XMM2,  XMM2b,  XMM2c,  XMM2d,
+                      XMM3,  XMM3b,  XMM3c,  XMM3d,
+                      XMM4,  XMM4b,  XMM4c,  XMM4d,
+                      XMM5,  XMM5b,  XMM5c,  XMM5d,
+                      XMM6,  XMM6b,  XMM6c,  XMM6d,
+                      XMM7,  XMM7b,  XMM7c,  XMM7d
+#ifdef _LP64
+                     ,XMM8,  XMM8b,  XMM8c,  XMM8d,
+                      XMM9,  XMM9b,  XMM9c,  XMM9d,
+                      XMM10, XMM10b, XMM10c, XMM10d,
+                      XMM11, XMM11b, XMM11c, XMM11d,
+                      XMM12, XMM12b, XMM12c, XMM12d,
+                      XMM13, XMM13b, XMM13c, XMM13d,
+                      XMM14, XMM14b, XMM14c, XMM14d,
+                      XMM15, XMM15b, XMM15c, XMM15d,
+                      XMM16, XMM16b, XMM16c, XMM16d,
+                      XMM17, XMM17b, XMM17c, XMM17d,
+                      XMM18, XMM18b, XMM18c, XMM18d,
+                      XMM19, XMM19b, XMM19c, XMM19d,
+                      XMM20, XMM20b, XMM20c, XMM20d,
+                      XMM21, XMM21b, XMM21c, XMM21d,
+                      XMM22, XMM22b, XMM22c, XMM22d,
+                      XMM23, XMM23b, XMM23c, XMM23d,
+                      XMM24, XMM24b, XMM24c, XMM24d,
+                      XMM25, XMM25b, XMM25c, XMM25d,
+                      XMM26, XMM26b, XMM26c, XMM26d,
+                      XMM27, XMM27b, XMM27c, XMM27d,
+                      XMM28, XMM28b, XMM28c, XMM28d,
+                      XMM29, XMM29b, XMM29c, XMM29d,
+                      XMM30, XMM30b, XMM30c, XMM30d,
+                      XMM31, XMM31b, XMM31c, XMM31d
+#endif
+                      );
+
+reg_class_dynamic vectorx_reg(vectorx_reg_evex, vectorx_reg_legacy, %{ VM_Version::supports_evex() %} );
+
 // Class for all 256bit vector registers
-reg_class vectory_reg(XMM0,  XMM0b,  XMM0c,  XMM0d,  XMM0e,  XMM0f,  XMM0g,  XMM0h,
+reg_class vectory_reg_legacy(XMM0,  XMM0b,  XMM0c,  XMM0d,  XMM0e,  XMM0f,  XMM0g,  XMM0h,
                       XMM1,  XMM1b,  XMM1c,  XMM1d,  XMM1e,  XMM1f,  XMM1g,  XMM1h,
                       XMM2,  XMM2b,  XMM2c,  XMM2d,  XMM2e,  XMM2f,  XMM2g,  XMM2h,
                       XMM3,  XMM3b,  XMM3c,  XMM3d,  XMM3e,  XMM3f,  XMM3g,  XMM3h,
@@ -472,6 +1438,82 @@
 #endif
                       );
 
+// Class for all 256bit vector registers
+reg_class vectory_reg_evex(XMM0,  XMM0b,  XMM0c,  XMM0d,  XMM0e,  XMM0f,  XMM0g,  XMM0h,
+                      XMM1,  XMM1b,  XMM1c,  XMM1d,  XMM1e,  XMM1f,  XMM1g,  XMM1h,
+                      XMM2,  XMM2b,  XMM2c,  XMM2d,  XMM2e,  XMM2f,  XMM2g,  XMM2h,
+                      XMM3,  XMM3b,  XMM3c,  XMM3d,  XMM3e,  XMM3f,  XMM3g,  XMM3h,
+                      XMM4,  XMM4b,  XMM4c,  XMM4d,  XMM4e,  XMM4f,  XMM4g,  XMM4h,
+                      XMM5,  XMM5b,  XMM5c,  XMM5d,  XMM5e,  XMM5f,  XMM5g,  XMM5h,
+                      XMM6,  XMM6b,  XMM6c,  XMM6d,  XMM6e,  XMM6f,  XMM6g,  XMM6h,
+                      XMM7,  XMM7b,  XMM7c,  XMM7d,  XMM7e,  XMM7f,  XMM7g,  XMM7h
+#ifdef _LP64
+                     ,XMM8,  XMM8b,  XMM8c,  XMM8d,  XMM8e,  XMM8f,  XMM8g,  XMM8h,
+                      XMM9,  XMM9b,  XMM9c,  XMM9d,  XMM9e,  XMM9f,  XMM9g,  XMM9h,
+                      XMM10, XMM10b, XMM10c, XMM10d, XMM10e, XMM10f, XMM10g, XMM10h,
+                      XMM11, XMM11b, XMM11c, XMM11d, XMM11e, XMM11f, XMM11g, XMM11h,
+                      XMM12, XMM12b, XMM12c, XMM12d, XMM12e, XMM12f, XMM12g, XMM12h,
+                      XMM13, XMM13b, XMM13c, XMM13d, XMM13e, XMM13f, XMM13g, XMM13h,
+                      XMM14, XMM14b, XMM14c, XMM14d, XMM14e, XMM14f, XMM14g, XMM14h,
+                      XMM15, XMM15b, XMM15c, XMM15d, XMM15e, XMM15f, XMM15g, XMM15h,
+                      XMM16, XMM16b, XMM16c, XMM16d, XMM16e, XMM16f, XMM16g, XMM16h,
+                      XMM17, XMM17b, XMM17c, XMM17d, XMM17e, XMM17f, XMM17g, XMM17h,
+                      XMM18, XMM18b, XMM18c, XMM18d, XMM18e, XMM18f, XMM18g, XMM18h,
+                      XMM19, XMM19b, XMM19c, XMM19d, XMM19e, XMM19f, XMM19g, XMM19h,
+                      XMM20, XMM20b, XMM20c, XMM20d, XMM20e, XMM20f, XMM20g, XMM20h,
+                      XMM21, XMM21b, XMM21c, XMM21d, XMM21e, XMM21f, XMM21g, XMM21h,
+                      XMM22, XMM22b, XMM22c, XMM22d, XMM22e, XMM22f, XMM22g, XMM22h,
+                      XMM23, XMM23b, XMM23c, XMM23d, XMM23e, XMM23f, XMM23g, XMM23h,
+                      XMM24, XMM24b, XMM24c, XMM24d, XMM24e, XMM24f, XMM24g, XMM24h,
+                      XMM25, XMM25b, XMM25c, XMM25d, XMM25e, XMM25f, XMM25g, XMM25h,
+                      XMM26, XMM26b, XMM26c, XMM26d, XMM26e, XMM26f, XMM26g, XMM26h,
+                      XMM27, XMM27b, XMM27c, XMM27d, XMM27e, XMM27f, XMM27g, XMM27h,
+                      XMM28, XMM28b, XMM28c, XMM28d, XMM28e, XMM28f, XMM28g, XMM28h,
+                      XMM29, XMM29b, XMM29c, XMM29d, XMM29e, XMM29f, XMM29g, XMM29h,
+                      XMM30, XMM30b, XMM30c, XMM30d, XMM30e, XMM30f, XMM30g, XMM30h,
+                      XMM31, XMM31b, XMM31c, XMM31d, XMM31e, XMM31f, XMM31g, XMM31h
+#endif
+                      );
+
+reg_class_dynamic vectory_reg(vectory_reg_evex, vectory_reg_legacy, %{ VM_Version::supports_evex() %} );
+
+// Class for all 512bit vector registers
+reg_class vectorz_reg(XMM0,  XMM0b,  XMM0c,  XMM0d,  XMM0e,  XMM0f,  XMM0g,  XMM0h,  XMM0i,  XMM0j,  XMM0k,  XMM0l,  XMM0m,  XMM0n,  XMM0o,  XMM0p,
+                      XMM1,  XMM1b,  XMM1c,  XMM1d,  XMM1e,  XMM1f,  XMM1g,  XMM1h,  XMM1i,  XMM1j,  XMM1k,  XMM1l,  XMM1m,  XMM1n,  XMM1o,  XMM1p,
+                      XMM2,  XMM2b,  XMM2c,  XMM2d,  XMM2e,  XMM2f,  XMM2g,  XMM2h,  XMM2i,  XMM2j,  XMM2k,  XMM2l,  XMM2m,  XMM2n,  XMM2o,  XMM2p,
+                      XMM3,  XMM3b,  XMM3c,  XMM3d,  XMM3e,  XMM3f,  XMM3g,  XMM3h,  XMM3i,  XMM3j,  XMM3k,  XMM3l,  XMM3m,  XMM3n,  XMM3o,  XMM3p,
+                      XMM4,  XMM4b,  XMM4c,  XMM4d,  XMM4e,  XMM4f,  XMM4g,  XMM4h,  XMM4i,  XMM4j,  XMM4k,  XMM4l,  XMM4m,  XMM4n,  XMM4o,  XMM4p,
+                      XMM5,  XMM5b,  XMM5c,  XMM5d,  XMM5e,  XMM5f,  XMM5g,  XMM5h,  XMM5i,  XMM5j,  XMM5k,  XMM5l,  XMM5m,  XMM5n,  XMM5o,  XMM5p,
+                      XMM6,  XMM6b,  XMM6c,  XMM6d,  XMM6e,  XMM6f,  XMM6g,  XMM6h,  XMM6i,  XMM6j,  XMM6k,  XMM6l,  XMM6m,  XMM6n,  XMM6o,  XMM6p,
+                      XMM7,  XMM7b,  XMM7c,  XMM7d,  XMM7e,  XMM7f,  XMM7g,  XMM7h,  XMM7i,  XMM7j,  XMM7k,  XMM7l,  XMM7m,  XMM7n,  XMM7o,  XMM7p
+#ifdef _LP64
+                     ,XMM8,  XMM8b,  XMM8c,  XMM8d,  XMM8e,  XMM8f,  XMM8g,  XMM8h,  XMM8i,  XMM8j,  XMM8k,  XMM8l,  XMM8m,  XMM8n,  XMM8o,  XMM8p,
+                      XMM9,  XMM9b,  XMM9c,  XMM9d,  XMM9e,  XMM9f,  XMM9g,  XMM9h,  XMM9i,  XMM9j,  XMM9k,  XMM9l,  XMM9m,  XMM9n,  XMM9o,  XMM9p,
+                      XMM10, XMM10b, XMM10c, XMM10d, XMM10e, XMM10f, XMM10g, XMM10h, XMM10i, XMM10j, XMM10k, XMM10l, XMM10m, XMM10n, XMM10o, XMM10p,
+                      XMM11, XMM11b, XMM11c, XMM11d, XMM11e, XMM11f, XMM11g, XMM11h, XMM11i, XMM11j, XMM11k, XMM11l, XMM11m, XMM11n, XMM11o, XMM11p,
+                      XMM12, XMM12b, XMM12c, XMM12d, XMM12e, XMM12f, XMM12g, XMM12h, XMM12i, XMM12j, XMM12k, XMM12l, XMM12m, XMM12n, XMM12o, XMM12p,
+                      XMM13, XMM13b, XMM13c, XMM13d, XMM13e, XMM13f, XMM13g, XMM13h, XMM13i, XMM13j, XMM13k, XMM13l, XMM13m, XMM13n, XMM13o, XMM13p,
+                      XMM14, XMM14b, XMM14c, XMM14d, XMM14e, XMM14f, XMM14g, XMM14h, XMM14i, XMM14j, XMM14k, XMM14l, XMM14m, XMM14n, XMM14o, XMM14p,
+                      XMM15, XMM15b, XMM15c, XMM15d, XMM15e, XMM15f, XMM15g, XMM15h, XMM15i, XMM15j, XMM15k, XMM15l, XMM15m, XMM15n, XMM15o, XMM15p
+                     ,XMM16, XMM16b, XMM16c, XMM16d, XMM16e, XMM16f, XMM16g, XMM16h, XMM16i, XMM16j, XMM16k, XMM16l, XMM16m, XMM16n, XMM16o, XMM16p,
+                      XMM17, XMM17b, XMM17c, XMM17d, XMM17e, XMM17f, XMM17g, XMM17h, XMM17i, XMM17j, XMM17k, XMM17l, XMM17m, XMM17n, XMM17o, XMM17p,
+                      XMM18, XMM18b, XMM18c, XMM18d, XMM18e, XMM18f, XMM18g, XMM18h, XMM18i, XMM18j, XMM18k, XMM18l, XMM18m, XMM18n, XMM18o, XMM18p,
+                      XMM19, XMM19b, XMM19c, XMM19d, XMM19e, XMM19f, XMM19g, XMM19h, XMM19i, XMM19j, XMM19k, XMM19l, XMM19m, XMM19n, XMM19o, XMM19p,
+                      XMM20, XMM20b, XMM20c, XMM20d, XMM20e, XMM20f, XMM20g, XMM20h, XMM20i, XMM20j, XMM20k, XMM20l, XMM20m, XMM20n, XMM20o, XMM20p,
+                      XMM21, XMM21b, XMM21c, XMM21d, XMM21e, XMM21f, XMM21g, XMM21h, XMM21i, XMM21j, XMM21k, XMM21l, XMM21m, XMM21n, XMM21o, XMM21p,
+                      XMM22, XMM22b, XMM22c, XMM22d, XMM22e, XMM22f, XMM22g, XMM22h, XMM22i, XMM22j, XMM22k, XMM22l, XMM22m, XMM22n, XMM22o, XMM22p,
+                      XMM23, XMM23b, XMM23c, XMM23d, XMM23e, XMM23f, XMM23g, XMM23h, XMM23i, XMM23j, XMM23k, XMM23l, XMM23m, XMM23n, XMM23o, XMM23p,
+                      XMM24, XMM24b, XMM24c, XMM24d, XMM24e, XMM24f, XMM24g, XMM24h, XMM24i, XMM24j, XMM24k, XMM24l, XMM24m, XMM24n, XMM24o, XMM24p,
+                      XMM25, XMM25b, XMM25c, XMM25d, XMM25e, XMM25f, XMM25g, XMM25h, XMM25i, XMM25j, XMM25k, XMM25l, XMM25m, XMM25n, XMM25o, XMM25p,
+                      XMM26, XMM26b, XMM26c, XMM26d, XMM26e, XMM26f, XMM26g, XMM26h, XMM26i, XMM26j, XMM26k, XMM26l, XMM26m, XMM26n, XMM26o, XMM26p,
+                      XMM27, XMM27b, XMM27c, XMM27d, XMM27e, XMM27f, XMM27g, XMM27h, XMM27i, XMM27j, XMM27k, XMM27l, XMM27m, XMM27n, XMM27o, XMM27p,
+                      XMM28, XMM28b, XMM28c, XMM28d, XMM28e, XMM28f, XMM28g, XMM28h, XMM28i, XMM28j, XMM28k, XMM28l, XMM28m, XMM28n, XMM28o, XMM28p,
+                      XMM29, XMM29b, XMM29c, XMM29d, XMM29e, XMM29f, XMM29g, XMM29h, XMM29i, XMM29j, XMM29k, XMM29l, XMM29m, XMM29n, XMM29o, XMM29p,
+                      XMM30, XMM30b, XMM30c, XMM30d, XMM30e, XMM30f, XMM30g, XMM30h, XMM30i, XMM30j, XMM30k, XMM30l, XMM30m, XMM30n, XMM30o, XMM30p,
+                      XMM31, XMM31b, XMM31c, XMM31d, XMM31e, XMM31f, XMM31g, XMM31h, XMM31i, XMM31j, XMM31k, XMM31l, XMM31m, XMM31n, XMM31o, XMM31p
+#endif
+                      );
+
 %}
 
 
@@ -623,6 +1665,10 @@
       if ((UseSSE < 4) && (UseAVX < 1)) // only with SSE4_1 or AVX
         return false;
     break;
+    case Op_MulVL:
+    case Op_MulReductionVL:
+      if (VM_Version::supports_avx512dq() == false)
+        return false;
     case Op_AddReductionVL:
       if (UseAVX < 3) // only EVEX : vector connectivity becomes an issue here
         return false;
@@ -657,10 +1703,11 @@
   if (UseSSE < 2) return 0;
   // SSE2 supports 128bit vectors for all types.
   // AVX2 supports 256bit vectors for all types.
-  int size = (UseAVX > 1) ? 32 : 16;
+  // AVX2/EVEX supports 512bit vectors for all types.
+  int size = (UseAVX > 1) ? (1 << UseAVX) * 8 : 16;
   // AVX1 supports 256bit vectors only for FLOAT and DOUBLE.
   if (UseAVX > 0 && (bt == T_FLOAT || bt == T_DOUBLE))
-    size = 32;
+    size = (UseAVX > 2) ? 64 : 32;
   // Use flag to limit vector size.
   size = MIN2(size,(int)MaxVectorSize);
   // Minimum 2 values in vector (or 4 for bytes).
@@ -702,6 +1749,7 @@
     case  8: return Op_VecD;
     case 16: return Op_VecX;
     case 32: return Op_VecY;
+    case 64: return Op_VecZ;
   }
   ShouldNotReachHere();
   return 0;
@@ -745,6 +1793,9 @@
     case Op_VecY:
       __ vmovdqu(as_XMMRegister(Matcher::_regEncode[dst_lo]), as_XMMRegister(Matcher::_regEncode[src_lo]));
       break;
+    case Op_VecZ:
+      __ evmovdqu(as_XMMRegister(Matcher::_regEncode[dst_lo]), as_XMMRegister(Matcher::_regEncode[src_lo]), 2);
+      break;
     default:
       ShouldNotReachHere();
     }
@@ -763,6 +1814,7 @@
       st->print("movdqu  %s,%s\t# spill",Matcher::regName[dst_lo],Matcher::regName[src_lo]);
       break;
     case Op_VecY:
+    case Op_VecZ:
       st->print("vmovdqu %s,%s\t# spill",Matcher::regName[dst_lo],Matcher::regName[src_lo]);
       break;
     default:
@@ -771,7 +1823,7 @@
 #endif
   }
   // VEX_2bytes prefix is used if UseAVX > 0, and it takes the same 2 bytes as SIMD prefix.
-  return 4;
+  return (UseAVX > 2) ? 6 : 4;
 }
 
 static int vec_spill_helper(CodeBuffer *cbuf, bool do_size, bool is_load,
@@ -796,6 +1848,9 @@
       case Op_VecY:
         __ vmovdqu(as_XMMRegister(Matcher::_regEncode[reg]), Address(rsp, stack_offset));
         break;
+      case Op_VecZ:
+        __ evmovdqu(as_XMMRegister(Matcher::_regEncode[reg]), Address(rsp, stack_offset), 2);
+        break;
       default:
         ShouldNotReachHere();
       }
@@ -813,13 +1868,16 @@
       case Op_VecY:
         __ vmovdqu(Address(rsp, stack_offset), as_XMMRegister(Matcher::_regEncode[reg]));
         break;
+      case Op_VecZ:
+        __ evmovdqu(Address(rsp, stack_offset), as_XMMRegister(Matcher::_regEncode[reg]), 2);
+        break;
       default:
         ShouldNotReachHere();
       }
     }
     int size = __ offset() - offset;
 #ifdef ASSERT
-    int offset_size = (stack_offset == 0) ? 0 : ((stack_offset < 0x80) ? 1 : 4);
+    int offset_size = (stack_offset == 0) ? 0 : ((stack_offset < 0x80) ? 1 : (UseAVX > 2) ? 6 : 4);
     // VEX_2bytes prefix is used if UseAVX > 0, so it takes the same 2 bytes as SIMD prefix.
     assert(!do_size || size == (5+offset_size), "incorrect size calculattion");
 #endif
@@ -838,6 +1896,7 @@
         st->print("movdqu  %s,[rsp + %d]\t# spill", Matcher::regName[reg], stack_offset);
         break;
       case Op_VecY:
+      case Op_VecZ:
         st->print("vmovdqu %s,[rsp + %d]\t# spill", Matcher::regName[reg], stack_offset);
         break;
       default:
@@ -855,6 +1914,7 @@
         st->print("movdqu  [rsp + %d],%s\t# spill", stack_offset, Matcher::regName[reg]);
         break;
       case Op_VecY:
+      case Op_VecZ:
         st->print("vmovdqu [rsp + %d],%s\t# spill", stack_offset, Matcher::regName[reg]);
         break;
       default:
@@ -863,7 +1923,7 @@
     }
 #endif
   }
-  int offset_size = (stack_offset == 0) ? 0 : ((stack_offset < 0x80) ? 1 : 4);
+  int offset_size = (stack_offset == 0) ? 0 : ((stack_offset < 0x80) ? 1 : (UseAVX > 2) ? 6 : 4);
   // VEX_2bytes prefix is used if UseAVX > 0, so it takes the same 2 bytes as SIMD prefix.
   return 5+offset_size;
 }
@@ -952,40 +2012,15 @@
 // in the ADLC because operands constitute user defined types which are used in
 // instruction definitions.
 
-// Vectors
-operand vecS() %{
-  constraint(ALLOC_IN_RC(vectors_reg));
-  match(VecS);
-
-  format %{ %}
-  interface(REG_INTER);
-%}
-
-operand vecD() %{
-  constraint(ALLOC_IN_RC(vectord_reg));
-  match(VecD);
+// This one generically applies only for evex, so only one version
+operand vecZ() %{
+  constraint(ALLOC_IN_RC(vectorz_reg));
+  match(VecZ);
 
   format %{ %}
   interface(REG_INTER);
 %}
 
-operand vecX() %{
-  constraint(ALLOC_IN_RC(vectorx_reg));
-  match(VecX);
-
-  format %{ %}
-  interface(REG_INTER);
-%}
-
-operand vecY() %{
-  constraint(ALLOC_IN_RC(vectory_reg));
-  match(VecY);
-
-  format %{ %}
-  interface(REG_INTER);
-%}
-
-
 // INSTRUCTIONS -- Platform independent definitions (same for 32- and 64-bit)
 
 // ============================================================================
@@ -1586,9 +2621,9 @@
   ins_cost(150);
   format %{ "vandps  $dst, $src, [0x7fffffff]\t# abs float by sign masking" %}
   ins_encode %{
-    bool vector256 = false;
+    int vector_len = 0;
     __ vandps($dst$$XMMRegister, $src$$XMMRegister,
-              ExternalAddress(float_signmask()), vector256);
+              ExternalAddress(float_signmask()), vector_len);
   %}
   ins_pipe(pipe_slow);
 %}
@@ -1612,9 +2647,9 @@
   format %{ "vandpd  $dst, $src, [0x7fffffffffffffff]\t"
             "# abs double by sign masking" %}
   ins_encode %{
-    bool vector256 = false;
+    int vector_len = 0;
     __ vandpd($dst$$XMMRegister, $src$$XMMRegister,
-              ExternalAddress(double_signmask()), vector256);
+              ExternalAddress(double_signmask()), vector_len);
   %}
   ins_pipe(pipe_slow);
 %}
@@ -1636,9 +2671,9 @@
   ins_cost(150);
   format %{ "vxorps  $dst, $src, [0x80000000]\t# neg float by sign flipping" %}
   ins_encode %{
-    bool vector256 = false;
+    int vector_len = 0;
     __ vxorps($dst$$XMMRegister, $src$$XMMRegister,
-              ExternalAddress(float_signflip()), vector256);
+              ExternalAddress(float_signflip()), vector_len);
   %}
   ins_pipe(pipe_slow);
 %}
@@ -1662,9 +2697,9 @@
   format %{ "vxorpd  $dst, $src, [0x8000000000000000]\t"
             "# neg double by sign flipping" %}
   ins_encode %{
-    bool vector256 = false;
+    int vector_len = 0;
     __ vxorpd($dst$$XMMRegister, $src$$XMMRegister,
-              ExternalAddress(double_signflip()), vector256);
+              ExternalAddress(double_signflip()), vector_len);
   %}
   ins_pipe(pipe_slow);
 %}
@@ -1739,7 +2774,6 @@
   ins_pipe(pipe_slow);
 %}
 
-
 // ====================VECTOR INSTRUCTIONS=====================================
 
 // Load vectors (4 bytes long)
@@ -1790,6 +2824,19 @@
   ins_pipe( pipe_slow );
 %}
 
+// Load vectors (64 bytes long)
+instruct loadV64(vecZ dst, memory mem) %{
+  predicate(n->as_LoadVector()->memory_size() == 64);
+  match(Set dst (LoadVector mem));
+  ins_cost(125);
+  format %{ "vmovdqu $dst k0,$mem\t! load vector (64 bytes)" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ evmovdqu($dst$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
 // Store vectors
 instruct storeV4(memory mem, vecS src) %{
   predicate(n->as_StoreVector()->memory_size() == 4);
@@ -1835,6 +2882,18 @@
   ins_pipe( pipe_slow );
 %}
 
+instruct storeV64(memory mem, vecZ src) %{
+  predicate(n->as_StoreVector()->memory_size() == 64);
+  match(Set mem (StoreVector mem src));
+  ins_cost(145);
+  format %{ "vmovdqu $mem k0,$src\t! store vector (64 bytes)" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ evmovdqu($mem$$Address, $src$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
 // Replicate byte scalar to be vector
 instruct Repl4B(vecS dst, rRegI src) %{
   predicate(n->as_Vector()->length() == 4);
@@ -1898,6 +2957,26 @@
   ins_pipe( pipe_slow );
 %}
 
+instruct Repl64B(vecZ dst, rRegI src) %{
+  predicate(n->as_Vector()->length() == 64);
+  match(Set dst (ReplicateB src));
+  format %{ "movd    $dst,$src\n\t"
+            "punpcklbw $dst,$dst\n\t"
+            "pshuflw $dst,$dst,0x00\n\t"
+            "punpcklqdq $dst,$dst\n\t"
+            "vinserti128h $dst,$dst,$dst\t! lower replicate32B\n\t"
+            "vinserti64x4h $dst k0,$dst,$dst\t! upper replicate632B" %}
+  ins_encode %{
+    __ movdl($dst$$XMMRegister, $src$$Register);
+    __ punpcklbw($dst$$XMMRegister, $dst$$XMMRegister);
+    __ pshuflw($dst$$XMMRegister, $dst$$XMMRegister, 0x00);
+    __ punpcklqdq($dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinserti128h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinserti64x4h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
 // Replicate byte scalar immediate to be vector by loading from const table.
 instruct Repl4B_imm(vecS dst, immI con) %{
   predicate(n->as_Vector()->length() == 4);
@@ -1945,6 +3024,22 @@
   ins_pipe( pipe_slow );
 %}
 
+instruct Repl64B_imm(vecZ dst, immI con) %{
+  predicate(n->as_Vector()->length() == 64);
+  match(Set dst (ReplicateB con));
+  format %{ "movq    $dst,[$constantaddress]\n\t"
+            "punpcklqdq $dst,$dst\n\t"
+            "vinserti128h $dst,$dst,$dst\t! lower replicate32B($con)\n\t"
+            "vinserti64x4h $dst k0,$dst,$dst\t! upper replicate32B($con)" %}
+  ins_encode %{
+    __ movq($dst$$XMMRegister, $constantaddress(replicate8_imm($con$$constant, 1)));
+    __ punpcklqdq($dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinserti128h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinserti64x4h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
 // Replicate byte scalar zero to be vector
 instruct Repl4B_zero(vecS dst, immI0 zero) %{
   predicate(n->as_Vector()->length() == 4);
@@ -1982,8 +3077,20 @@
   format %{ "vpxor   $dst,$dst,$dst\t! replicate32B zero" %}
   ins_encode %{
     // Use vxorpd since AVX does not have vpxor for 256-bit (AVX2 will have it).
-    bool vector256 = true;
-    __ vpxor($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpxor($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister, vector_len);
+  %}
+  ins_pipe( fpu_reg_reg );
+%}
+
+instruct Repl64B_zero(vecZ dst, immI0 zero) %{
+  predicate(n->as_Vector()->length() == 64);
+  match(Set dst (ReplicateB zero));
+  format %{ "vpxor   $dst k0,$dst,$dst\t! replicate64B zero" %}
+  ins_encode %{
+    // Use vxorpd since AVX does not have vpxor for 512-bit (EVEX will have it).
+    int vector_len = 2;
+    __ vpxor($dst$$XMMRegister,$dst$$XMMRegister, $dst$$XMMRegister, vector_len);
   %}
   ins_pipe( fpu_reg_reg );
 %}
@@ -2043,6 +3150,24 @@
   ins_pipe( pipe_slow );
 %}
 
+instruct Repl32S(vecZ dst, rRegI src) %{
+  predicate(n->as_Vector()->length() == 32);
+  match(Set dst (ReplicateS src));
+  format %{ "movd    $dst,$src\n\t"
+            "pshuflw $dst,$dst,0x00\n\t"
+            "punpcklqdq $dst,$dst\n\t"
+            "vinserti128h $dst,$dst,$dst\t! lower replicate16S\n\t"
+            "vinserti64x4h $dst k0,$dst,$dst\t! upper replicate16S" %}
+  ins_encode %{
+    __ movdl($dst$$XMMRegister, $src$$Register);
+    __ pshuflw($dst$$XMMRegister, $dst$$XMMRegister, 0x00);
+    __ punpcklqdq($dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinserti128h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinserti64x4h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
 // Replicate char/short (2 byte) scalar immediate to be vector by loading from const table.
 instruct Repl2S_imm(vecS dst, immI con) %{
   predicate(n->as_Vector()->length() == 2);
@@ -2090,6 +3215,22 @@
   ins_pipe( pipe_slow );
 %}
 
+instruct Repl32S_imm(vecZ dst, immI con) %{
+  predicate(n->as_Vector()->length() == 32);
+  match(Set dst (ReplicateS con));
+  format %{ "movq    $dst,[$constantaddress]\n\t"
+            "punpcklqdq $dst,$dst\n\t"
+            "vinserti128h $dst,$dst,$dst\t! lower replicate16S($con)\n\t"
+            "vinserti64x4h $dst k0,$dst,$dst\t! upper replicate16S($con)" %}
+  ins_encode %{
+    __ movq($dst$$XMMRegister, $constantaddress(replicate8_imm($con$$constant, 2)));
+    __ punpcklqdq($dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinserti128h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinserti64x4h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
 // Replicate char/short (2 byte) scalar zero to be vector
 instruct Repl2S_zero(vecS dst, immI0 zero) %{
   predicate(n->as_Vector()->length() == 2);
@@ -2127,8 +3268,20 @@
   format %{ "vpxor   $dst,$dst,$dst\t! replicate16S zero" %}
   ins_encode %{
     // Use vxorpd since AVX does not have vpxor for 256-bit (AVX2 will have it).
-    bool vector256 = true;
-    __ vpxor($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpxor($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister, vector_len);
+  %}
+  ins_pipe( fpu_reg_reg );
+%}
+
+instruct Repl32S_zero(vecZ dst, immI0 zero) %{
+  predicate(n->as_Vector()->length() == 32);
+  match(Set dst (ReplicateS zero));
+  format %{ "vpxor   $dst k0,$dst,$dst\t! replicate32S zero" %}
+  ins_encode %{
+    // Use vxorpd since AVX does not have vpxor for 512-bit (EVEX will have it).
+    int vector_len = 2;
+    __ vpxor($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister, vector_len);
   %}
   ins_pipe( fpu_reg_reg );
 %}
@@ -2172,6 +3325,22 @@
   ins_pipe( pipe_slow );
 %}
 
+instruct Repl16I(vecZ dst, rRegI src) %{
+  predicate(n->as_Vector()->length() == 16);
+  match(Set dst (ReplicateI src));
+  format %{ "movd    $dst,$src\n\t"
+            "pshufd  $dst,$dst,0x00\n\t"
+            "vinserti128h $dst,$dst,$dst\t! lower replicate8I\n\t"
+            "vinserti64x4h $dst k0,$dst,$dst\t! upper replicate8I" %}
+  ins_encode %{
+    __ movdl($dst$$XMMRegister, $src$$Register);
+    __ pshufd($dst$$XMMRegister, $dst$$XMMRegister, 0x00);
+    __ vinserti128h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinserti64x4h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
 // Replicate integer (4 byte) scalar immediate to be vector by loading from const table.
 instruct Repl2I_imm(vecD dst, immI con) %{
   predicate(n->as_Vector()->length() == 2);
@@ -2209,6 +3378,22 @@
   ins_pipe( pipe_slow );
 %}
 
+instruct Repl16I_imm(vecZ dst, immI con) %{
+  predicate(n->as_Vector()->length() == 16);
+  match(Set dst (ReplicateI con));
+  format %{ "movq    $dst,[$constantaddress]\t! replicate16I($con)\n\t"
+            "punpcklqdq $dst,$dst\n\t"
+            "vinserti128h $dst,$dst,$dst\n\t"
+            "vinserti64x4h $dst k0,$dst,$dst" %}
+  ins_encode %{
+    __ movq($dst$$XMMRegister, $constantaddress(replicate8_imm($con$$constant, 4)));
+    __ punpcklqdq($dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinserti128h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinserti64x4h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
 // Integer could be loaded into xmm register directly from memory.
 instruct Repl2I_mem(vecD dst, memory mem) %{
   predicate(n->as_Vector()->length() == 2);
@@ -2248,6 +3433,22 @@
   ins_pipe( pipe_slow );
 %}
 
+instruct Repl16I_mem(vecZ dst, memory mem) %{
+  predicate(n->as_Vector()->length() == 16);
+  match(Set dst (ReplicateI (LoadI mem)));
+  format %{ "movd    $dst,$mem\n\t"
+            "pshufd  $dst,$dst,0x00\n\t"
+            "vinserti128h $dst,$dst,$dst\t! lower replicate8I\n\t"
+            "vinserti64x4h $dst k0,$dst,$dst\t! upper replicate8I" %}
+  ins_encode %{
+    __ movdl($dst$$XMMRegister, $mem$$Address);
+    __ pshufd($dst$$XMMRegister, $dst$$XMMRegister, 0x00);
+    __ vinserti128h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinserti64x4h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
 // Replicate integer (4 byte) scalar zero to be vector
 instruct Repl2I_zero(vecD dst, immI0 zero) %{
   predicate(n->as_Vector()->length() == 2);
@@ -2275,8 +3476,20 @@
   format %{ "vpxor   $dst,$dst,$dst\t! replicate8I zero" %}
   ins_encode %{
     // Use vxorpd since AVX does not have vpxor for 256-bit (AVX2 will have it).
-    bool vector256 = true;
-    __ vpxor($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpxor($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister, vector_len);
+  %}
+  ins_pipe( fpu_reg_reg );
+%}
+
+instruct Repl16I_zero(vecZ dst, immI0 zero) %{
+  predicate(n->as_Vector()->length() == 16);
+  match(Set dst (ReplicateI zero));
+  format %{ "vpxor   $dst k0,$dst,$dst\t! replicate16I zero" %}
+  ins_encode %{
+    // Use vxorpd since AVX does not have vpxor for 512-bit (AVX2 will have it).
+    int vector_len = 2;
+    __ vpxor($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister, vector_len);
   %}
   ins_pipe( fpu_reg_reg );
 %}
@@ -2308,6 +3521,22 @@
   %}
   ins_pipe( pipe_slow );
 %}
+
+instruct Repl8L(vecZ dst, rRegL src) %{
+  predicate(n->as_Vector()->length() == 8);
+  match(Set dst (ReplicateL src));
+  format %{ "movdq   $dst,$src\n\t"
+            "punpcklqdq $dst,$dst\n\t"
+            "vinserti128h $dst,$dst,$dst\t! lower replicate4L\n\t"
+            "vinserti64x4h $dst k0,$dst,$dst\t! upper replicate4L" %}
+  ins_encode %{
+    __ movdq($dst$$XMMRegister, $src$$Register);
+    __ punpcklqdq($dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinserti128h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinserti64x4h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
 #else // _LP64
 instruct Repl2L(vecX dst, eRegL src, regD tmp) %{
   predicate(n->as_Vector()->length() == 2);
@@ -2344,6 +3573,26 @@
   %}
   ins_pipe( pipe_slow );
 %}
+
+instruct Repl8L(vecZ dst, eRegL src, regD tmp) %{
+  predicate(n->as_Vector()->length() == 4);
+  match(Set dst (ReplicateL src));
+  effect(TEMP dst, USE src, TEMP tmp);
+  format %{ "movdl   $dst,$src.lo\n\t"
+            "movdl   $tmp,$src.hi\n\t"
+            "punpckldq $dst,$tmp\n\t"
+            "vinserti128h $dst,$dst,$dst\t! lower replicate4L\n\t"
+            "vinserti64x4h $dst k0,$dst,$dst\t! upper replicate4L" %}
+  ins_encode %{
+    __ movdl($dst$$XMMRegister, $src$$Register);
+    __ movdl($tmp$$XMMRegister, HIGH_FROM_LOW($src$$Register));
+    __ punpckldq($dst$$XMMRegister, $tmp$$XMMRegister);
+    __ punpcklqdq($dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinserti128h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinserti64x4h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
 #endif // _LP64
 
 // Replicate long (8 byte) scalar immediate to be vector by loading from const table.
@@ -2373,6 +3622,22 @@
   ins_pipe( pipe_slow );
 %}
 
+instruct Repl8L_imm(vecZ dst, immL con) %{
+  predicate(n->as_Vector()->length() == 8);
+  match(Set dst (ReplicateL con));
+  format %{ "movq    $dst,[$constantaddress]\n\t"
+            "punpcklqdq $dst,$dst\n\t"
+            "vinserti128h $dst,$dst,$dst\t! lower replicate4L($con)\n\t"
+            "vinserti64x4h $dst k0,$dst,$dst\t! upper replicate4L($con)" %}
+  ins_encode %{
+    __ movq($dst$$XMMRegister, $constantaddress($con));
+    __ punpcklqdq($dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinserti128h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinserti64x4h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
 // Long could be loaded into xmm register directly from memory.
 instruct Repl2L_mem(vecX dst, memory mem) %{
   predicate(n->as_Vector()->length() == 2);
@@ -2400,6 +3665,22 @@
   ins_pipe( pipe_slow );
 %}
 
+instruct Repl8L_mem(vecZ dst, memory mem) %{
+  predicate(n->as_Vector()->length() == 8);
+  match(Set dst (ReplicateL (LoadL mem)));
+  format %{ "movq    $dst,$mem\n\t"
+            "punpcklqdq $dst,$dst\n\t"
+            "vinserti128h $dst,$dst,$dst\t! lower replicate4L\n\t"
+            "vinserti64x4h $dst k0,$dst,$dst\t! upper replicate4L" %}
+  ins_encode %{
+    __ movq($dst$$XMMRegister, $mem$$Address);
+    __ punpcklqdq($dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinserti128h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinserti64x4h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
 // Replicate long (8 byte) scalar zero to be vector
 instruct Repl2L_zero(vecX dst, immL0 zero) %{
   predicate(n->as_Vector()->length() == 2);
@@ -2417,8 +3698,20 @@
   format %{ "vpxor   $dst,$dst,$dst\t! replicate4L zero" %}
   ins_encode %{
     // Use vxorpd since AVX does not have vpxor for 256-bit (AVX2 will have it).
-    bool vector256 = true;
-    __ vpxor($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpxor($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister, vector_len);
+  %}
+  ins_pipe( fpu_reg_reg );
+%}
+
+instruct Repl8L_zero(vecZ dst, immL0 zero) %{
+  predicate(n->as_Vector()->length() == 8);
+  match(Set dst (ReplicateL zero));
+  format %{ "vpxor   $dst k0,$dst,$dst\t! replicate8L zero" %}
+  ins_encode %{
+    // Use vxorpd since AVX does not have vpxor for 512-bit (EVEX will have it).
+    int vector_len = 2;
+    __ vpxor($dst$$XMMRegister,$dst$$XMMRegister, $dst$$XMMRegister, vector_len);
   %}
   ins_pipe( fpu_reg_reg );
 %}
@@ -2456,6 +3749,20 @@
   ins_pipe( pipe_slow );
 %}
 
+instruct Repl16F(vecZ dst, regF src) %{
+  predicate(n->as_Vector()->length() == 16);
+  match(Set dst (ReplicateF src));
+  format %{ "pshufd  $dst,$src,0x00\n\t"
+            "vinsertf128h $dst,$dst,$dst\t! lower replicate8F\n\t"
+            "vinsertf64x4h $dst k0,$dst,$dst\t! lower replicate8F" %}
+  ins_encode %{
+    __ pshufd($dst$$XMMRegister, $src$$XMMRegister, 0x00);
+    __ vinsertf128h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinsertf64x4h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
 // Replicate float (4 byte) scalar zero to be vector
 instruct Repl2F_zero(vecD dst, immF0 zero) %{
   predicate(n->as_Vector()->length() == 2);
@@ -2482,8 +3789,19 @@
   match(Set dst (ReplicateF zero));
   format %{ "vxorps  $dst,$dst,$dst\t! replicate8F zero" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vxorps($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vxorps($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister, vector_len);
+  %}
+  ins_pipe( fpu_reg_reg );
+%}
+
+instruct Repl16F_zero(vecZ dst, immF0 zero) %{
+  predicate(n->as_Vector()->length() == 16);
+  match(Set dst (ReplicateF zero));
+  format %{ "vxorps  $dst k0,$dst,$dst\t! replicate16F zero" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vxorps($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister, vector_len);
   %}
   ins_pipe( fpu_reg_reg );
 %}
@@ -2511,6 +3829,20 @@
   ins_pipe( pipe_slow );
 %}
 
+instruct Repl8D(vecZ dst, regD src) %{
+  predicate(n->as_Vector()->length() == 8);
+  match(Set dst (ReplicateD src));
+  format %{ "pshufd  $dst,$src,0x44\n\t"
+            "vinsertf128h $dst,$dst,$dst\t! lower replicate4D\n\t"
+            "vinsertf64x4h $dst k0,$dst,$dst\t! upper replicate4D" %}
+  ins_encode %{
+    __ pshufd($dst$$XMMRegister, $src$$XMMRegister, 0x44);
+    __ vinsertf128h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+    __ vinsertf64x4h($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
 // Replicate double (8 byte) scalar zero to be vector
 instruct Repl2D_zero(vecX dst, immD0 zero) %{
   predicate(n->as_Vector()->length() == 2);
@@ -2527,8 +3859,19 @@
   match(Set dst (ReplicateD zero));
   format %{ "vxorpd  $dst,$dst,$dst,vect256\t! replicate4D zero" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vxorpd($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vxorpd($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister, vector_len);
+  %}
+  ins_pipe( fpu_reg_reg );
+%}
+
+instruct Repl8D_zero(vecZ dst, immD0 zero) %{
+  predicate(n->as_Vector()->length() == 8);
+  match(Set dst (ReplicateD zero));
+  format %{ "vxorpd  $dst k0,$dst,$dst,vect512\t! replicate8D zero" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vxorpd($dst$$XMMRegister, $dst$$XMMRegister, $dst$$XMMRegister, vector_len);
   %}
   ins_pipe( fpu_reg_reg );
 %}
@@ -2555,17 +3898,38 @@
 %}
 
 instruct rvadd2I_reduction_reg(rRegI dst, rRegI src1, vecD src2, regF tmp, regF tmp2) %{
-  predicate(UseAVX > 0);
+  predicate(UseAVX > 0 && UseAVX < 3);
   match(Set dst (AddReductionVI src1 src2));
   effect(TEMP tmp, TEMP tmp2);
-  format %{ "vphaddd $tmp,$src2,$src2\n\t"
+  format %{ "vphaddd  $tmp,$src2,$src2\n\t"
+            "movd     $tmp2,$src1\n\t"
+            "vpaddd   $tmp2,$tmp2,$tmp\n\t"
+            "movd     $dst,$tmp2\t! add reduction2I" %}
+  ins_encode %{
+    int vector_len = 0;
+    __ vphaddd($tmp$$XMMRegister, $src2$$XMMRegister, $src2$$XMMRegister, vector_len);
+    __ movdl($tmp2$$XMMRegister, $src1$$Register);
+    __ vpaddd($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister, vector_len);
+    __ movdl($dst$$Register, $tmp2$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct rvadd2I_reduction_reg_evex(rRegI dst, rRegI src1, vecD src2, regF tmp, regF tmp2) %{
+  predicate(UseAVX > 2);
+  match(Set dst (AddReductionVI src1 src2));
+  effect(TEMP tmp, TEMP tmp2);
+  format %{ "pshufd  $tmp2,$src2,0x1\n\t"
+            "vpaddd  $tmp,$src2,$tmp2\n\t"
             "movd    $tmp2,$src1\n\t"
-            "vpaddd  $tmp2,$tmp2,$tmp\n\t"
+            "vpaddd  $tmp2,$tmp,$tmp2\n\t"
             "movd    $dst,$tmp2\t! add reduction2I" %}
   ins_encode %{
-    __ vphaddd($tmp$$XMMRegister, $src2$$XMMRegister, $src2$$XMMRegister, false);
+    int vector_len = 0;
+    __ pshufd($tmp2$$XMMRegister, $src2$$XMMRegister, 0x1);
+    __ vpaddd($tmp$$XMMRegister, $src2$$XMMRegister, $tmp2$$XMMRegister, vector_len);
     __ movdl($tmp2$$XMMRegister, $src1$$Register);
-    __ vpaddd($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister, false);
+    __ vpaddd($tmp2$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, vector_len);
     __ movdl($dst$$Register, $tmp2$$XMMRegister);
   %}
   ins_pipe( pipe_slow );
@@ -2593,47 +3957,203 @@
 %}
 
 instruct rvadd4I_reduction_reg(rRegI dst, rRegI src1, vecX src2, regF tmp, regF tmp2) %{
-  predicate(UseAVX > 0);
+  predicate(UseAVX > 0 && UseAVX < 3);
   match(Set dst (AddReductionVI src1 src2));
   effect(TEMP tmp, TEMP tmp2);
-  format %{ "vphaddd $tmp,$src2,$src2\n\t"
-            "vphaddd $tmp,$tmp,$tmp2\n\t"
+  format %{ "vphaddd  $tmp,$src2,$src2\n\t"
+            "vphaddd  $tmp,$tmp,$tmp2\n\t"
+            "movd     $tmp2,$src1\n\t"
+            "vpaddd   $tmp2,$tmp2,$tmp\n\t"
+            "movd     $dst,$tmp2\t! add reduction4I" %}
+  ins_encode %{
+    int vector_len = 0;
+    __ vphaddd($tmp$$XMMRegister, $src2$$XMMRegister, $src2$$XMMRegister, vector_len);
+    __ vphaddd($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, vector_len);
+    __ movdl($tmp2$$XMMRegister, $src1$$Register);
+    __ vpaddd($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister, vector_len);
+    __ movdl($dst$$Register, $tmp2$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct rvadd4I_reduction_reg_evex(rRegI dst, rRegI src1, vecX src2, regF tmp, regF tmp2) %{
+  predicate(UseAVX > 2);
+  match(Set dst (AddReductionVI src1 src2));
+  effect(TEMP tmp, TEMP tmp2);
+  format %{ "pshufd  $tmp2,$src2,0xE\n\t"
+            "vpaddd  $tmp,$src2,$tmp2\n\t"
+            "pshufd  $tmp2,$tmp,0x1\n\t"
+            "vpaddd  $tmp,$tmp,$tmp2\n\t"
             "movd    $tmp2,$src1\n\t"
-            "vpaddd  $tmp2,$tmp2,$tmp\n\t"
+            "vpaddd  $tmp2,$tmp,$tmp2\n\t"
             "movd    $dst,$tmp2\t! add reduction4I" %}
   ins_encode %{
-    __ vphaddd($tmp$$XMMRegister, $src2$$XMMRegister, $src2$$XMMRegister, false);
-    __ vphaddd($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, false);
+    int vector_len = 0;
+    __ pshufd($tmp2$$XMMRegister, $src2$$XMMRegister, 0xE);
+    __ vpaddd($tmp$$XMMRegister, $src2$$XMMRegister, $tmp2$$XMMRegister, vector_len);
+    __ pshufd($tmp2$$XMMRegister, $tmp$$XMMRegister, 0x1);
+    __ vpaddd($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, vector_len);
     __ movdl($tmp2$$XMMRegister, $src1$$Register);
-    __ vpaddd($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister, false);
+    __ vpaddd($tmp2$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, vector_len);
     __ movdl($dst$$Register, $tmp2$$XMMRegister);
   %}
   ins_pipe( pipe_slow );
 %}
 
 instruct rvadd8I_reduction_reg(rRegI dst, rRegI src1, vecY src2, regF tmp, regF tmp2) %{
-  predicate(UseAVX > 0);
+  predicate(UseAVX > 0 && UseAVX < 3);
+  match(Set dst (AddReductionVI src1 src2));
+  effect(TEMP tmp, TEMP tmp2);
+  format %{ "vphaddd  $tmp,$src2,$src2\n\t"
+            "vphaddd  $tmp,$tmp,$tmp2\n\t"
+            "vextracti128  $tmp2,$tmp\n\t"
+            "vpaddd   $tmp,$tmp,$tmp2\n\t"
+            "movd     $tmp2,$src1\n\t"
+            "vpaddd   $tmp2,$tmp2,$tmp\n\t"
+            "movd     $dst,$tmp2\t! add reduction8I" %}
+  ins_encode %{
+    int vector_len = 1;
+    __ vphaddd($tmp$$XMMRegister, $src2$$XMMRegister, $src2$$XMMRegister, vector_len);
+    __ vphaddd($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, vector_len);
+    __ vextracti128h($tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ vpaddd($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, 0);
+    __ movdl($tmp2$$XMMRegister, $src1$$Register);
+    __ vpaddd($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister, 0);
+    __ movdl($dst$$Register, $tmp2$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct rvadd8I_reduction_reg_evex(rRegI dst, rRegI src1, vecY src2, regF tmp, regF tmp2) %{
+  predicate(UseAVX > 2);
   match(Set dst (AddReductionVI src1 src2));
   effect(TEMP tmp, TEMP tmp2);
-  format %{ "vphaddd $tmp,$src2,$src2\n\t"
-            "vphaddd $tmp,$tmp,$tmp2\n\t"
-            "vextractf128  $tmp2,$tmp\n\t"
+  format %{ "vextracti128  $tmp,$src2\n\t"
+            "vpaddd  $tmp,$tmp,$src2\n\t"
+            "pshufd  $tmp2,$tmp,0xE\n\t"
+            "vpaddd  $tmp,$tmp,$tmp2\n\t"
+            "pshufd  $tmp2,$tmp,0x1\n\t"
+            "vpaddd  $tmp,$tmp,$tmp2\n\t"
+            "movd    $tmp2,$src1\n\t"
+            "vpaddd  $tmp2,$tmp,$tmp2\n\t"
+            "movd    $dst,$tmp2\t! add reduction8I" %}
+  ins_encode %{
+    int vector_len = 0;
+    __ vextracti128h($tmp$$XMMRegister, $src2$$XMMRegister);
+    __ vpaddd($tmp$$XMMRegister, $tmp$$XMMRegister, $src2$$XMMRegister, vector_len);
+    __ pshufd($tmp2$$XMMRegister, $tmp$$XMMRegister, 0xE);
+    __ vpaddd($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, vector_len);
+    __ pshufd($tmp2$$XMMRegister, $tmp$$XMMRegister, 0x1);
+    __ vpaddd($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, vector_len);
+    __ movdl($tmp2$$XMMRegister, $src1$$Register);
+    __ vpaddd($tmp2$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, vector_len);
+    __ movdl($dst$$Register, $tmp2$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct rvadd16I_reduction_reg_evex(rRegI dst, rRegI src1, vecZ src2, regF tmp, regF tmp2, regF tmp3) %{
+  predicate(UseAVX > 2);
+  match(Set dst (AddReductionVI src1 src2));
+  effect(TEMP tmp, TEMP tmp2, TEMP tmp3);
+  format %{ "vextracti64x4  $tmp3,$src2\n\t"
+            "vpaddd  $tmp3,$tmp3,$src2\n\t"
+            "vextracti128   $tmp,$tmp3\n\t"
+            "vpaddd  $tmp,$tmp,$tmp3\n\t"
+            "pshufd  $tmp2,$tmp,0xE\n\t"
+            "vpaddd  $tmp,$tmp,$tmp2\n\t"
+            "pshufd  $tmp2,$tmp,0x1\n\t"
             "vpaddd  $tmp,$tmp,$tmp2\n\t"
             "movd    $tmp2,$src1\n\t"
-            "vpaddd  $tmp2,$tmp2,$tmp\n\t"
-            "movd    $dst,$tmp2\t! add reduction8I" %}
-  ins_encode %{
-    __ vphaddd($tmp$$XMMRegister, $src2$$XMMRegister, $src2$$XMMRegister, true);
-    __ vphaddd($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, true);
-    __ vextractf128h($tmp2$$XMMRegister, $tmp$$XMMRegister);
-    __ vpaddd($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, false);
+            "vpaddd  $tmp2,$tmp,$tmp2\n\t"
+            "movd    $dst,$tmp2\t! mul reduction16I" %}
+  ins_encode %{
+    __ vextracti64x4h($tmp3$$XMMRegister, $src2$$XMMRegister);
+    __ vpaddd($tmp3$$XMMRegister, $tmp3$$XMMRegister, $src2$$XMMRegister, 1);
+    __ vextracti128h($tmp$$XMMRegister, $tmp3$$XMMRegister);
+    __ vpaddd($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp3$$XMMRegister, 0);
+    __ pshufd($tmp2$$XMMRegister, $tmp$$XMMRegister, 0xE);
+    __ vpaddd($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, 0);
+    __ pshufd($tmp2$$XMMRegister, $tmp$$XMMRegister, 0x1);
+    __ vpaddd($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, 0);
     __ movdl($tmp2$$XMMRegister, $src1$$Register);
-    __ vpaddd($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister, false);
+    __ vpaddd($tmp2$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, 0);
     __ movdl($dst$$Register, $tmp2$$XMMRegister);
   %}
   ins_pipe( pipe_slow );
 %}
 
+#ifdef _LP64
+instruct rvadd2L_reduction_reg(rRegL dst, rRegL src1, vecX src2, regF tmp, regF tmp2) %{
+  predicate(UseAVX > 2);
+  match(Set dst (AddReductionVL src1 src2));
+  effect(TEMP tmp, TEMP tmp2);
+  format %{ "pshufd  $tmp2,$src2,0xE\n\t"
+            "vpaddq  $tmp,$src2,$tmp2\n\t"
+            "movdq   $tmp2,$src1\n\t"
+            "vpaddq  $tmp2,$tmp,$tmp2\n\t"
+            "movdq   $dst,$tmp2\t! add reduction2L" %}
+  ins_encode %{
+    __ pshufd($tmp2$$XMMRegister, $src2$$XMMRegister, 0xE);
+    __ vpaddq($tmp$$XMMRegister, $src2$$XMMRegister, $tmp2$$XMMRegister, 0);
+    __ movdq($tmp2$$XMMRegister, $src1$$Register);
+    __ vpaddq($tmp2$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, 0);
+    __ movdq($dst$$Register, $tmp2$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct rvadd4L_reduction_reg(rRegL dst, rRegL src1, vecY src2, regF tmp, regF tmp2) %{
+  predicate(UseAVX > 2);
+  match(Set dst (AddReductionVL src1 src2));
+  effect(TEMP tmp, TEMP tmp2);
+  format %{ "vextracti64x2  $tmp,$src2, 0x1\n\t"
+            "vpaddq  $tmp2,$tmp,$src2\n\t"
+            "pshufd  $tmp,$tmp2,0xE\n\t"
+            "vpaddq  $tmp2,$tmp2,$tmp\n\t"
+            "movdq   $tmp,$src1\n\t"
+            "vpaddq  $tmp2,$tmp2,$tmp\n\t"
+            "movdq   $dst,$tmp2\t! add reduction4L" %}
+  ins_encode %{
+    __ vextracti64x2h($tmp$$XMMRegister, $src2$$XMMRegister, 0x1);
+    __ vpaddq($tmp2$$XMMRegister, $tmp$$XMMRegister, $src2$$XMMRegister, 0);
+    __ pshufd($tmp$$XMMRegister, $tmp2$$XMMRegister, 0xE);
+    __ vpaddq($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister, 0);
+    __ movdq($tmp$$XMMRegister, $src1$$Register);
+    __ vpaddq($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister, 0);
+    __ movdq($dst$$Register, $tmp2$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct rvadd8L_reduction_reg(rRegL dst, rRegL src1, vecZ src2, regF tmp, regF tmp2) %{
+  predicate(UseAVX > 2);
+  match(Set dst (AddReductionVL src1 src2));
+  effect(TEMP tmp, TEMP tmp2);
+  format %{ "vextracti64x4  $tmp2,$src2\n\t"
+            "vpaddq  $tmp2,$tmp2,$src2\n\t"
+            "vextracti128   $tmp,$tmp2\n\t"
+            "vpaddq  $tmp2,$tmp2,$tmp\n\t"
+            "pshufd  $tmp,$tmp2,0xE\n\t"
+            "vpaddq  $tmp2,$tmp2,$tmp\n\t"
+            "movdq   $tmp,$src1\n\t"
+            "vpaddq  $tmp2,$tmp2,$tmp\n\t"
+            "movdq   $dst,$tmp2\t! add reduction8L" %}
+  ins_encode %{
+    __ vextracti64x4h($tmp2$$XMMRegister, $src2$$XMMRegister);
+    __ vpaddq($tmp2$$XMMRegister, $tmp2$$XMMRegister, $src2$$XMMRegister, 1);
+    __ vextracti128h($tmp$$XMMRegister, $tmp2$$XMMRegister);
+    __ vpaddq($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister, 0);
+    __ pshufd($tmp$$XMMRegister, $tmp2$$XMMRegister, 0xE);
+    __ vpaddq($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister, 0);
+    __ movdq($tmp$$XMMRegister, $src1$$Register);
+    __ vpaddq($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister, 0);
+    __ movdq($dst$$Register, $tmp2$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+#endif
+
 instruct rsadd2F_reduction_reg(regF dst, regF src1, vecD src2, regF tmp, regF tmp2) %{
   predicate(UseSSE >= 1 && UseAVX == 0);
   match(Set dst (AddReductionVF src1 src2));
@@ -2757,6 +4277,77 @@
   ins_pipe( pipe_slow );
 %}
 
+instruct radd16F_reduction_reg(regF dst, regF src1, vecZ src2, regF tmp, regF tmp2, regF tmp3) %{
+  predicate(UseAVX > 2);
+  match(Set dst (AddReductionVF src1 src2));
+  effect(TEMP tmp, TEMP tmp2, TEMP tmp3);
+  format %{ "vaddss  $tmp2,$src1,$src2\n\t"
+            "pshufd  $tmp,$src2,0x01\n\t"
+            "vaddss  $tmp2,$tmp2,$tmp\n\t"
+            "pshufd  $tmp,$src2,0x02\n\t"
+            "vaddss  $tmp2,$tmp2,$tmp\n\t"
+            "pshufd  $tmp,$src2,0x03\n\t"
+            "vaddss  $tmp2,$tmp2,$tmp\n\t"
+            "vextractf64x2  $tmp3,$src2, 0x1\n\t"
+            "vaddss  $tmp2,$tmp2,$tmp3\n\t"
+            "pshufd  $tmp,$tmp3,0x01\n\t"
+            "vaddss  $tmp2,$tmp2,$tmp\n\t"
+            "pshufd  $tmp,$tmp3,0x02\n\t"
+            "vaddss  $tmp2,$tmp2,$tmp\n\t"
+            "pshufd  $tmp,$tmp3,0x03\n\t"
+            "vaddss  $tmp2,$tmp2,$tmp\n\t"
+            "vextractf64x2  $tmp3,$src2, 0x2\n\t"
+            "vaddss  $tmp2,$tmp2,$tmp3\n\t"
+            "pshufd  $tmp,$tmp3,0x01\n\t"
+            "vaddss  $tmp2,$tmp2,$tmp\n\t"
+            "pshufd  $tmp,$tmp3,0x02\n\t"
+            "vaddss  $tmp2,$tmp2,$tmp\n\t"
+            "pshufd  $tmp,$tmp3,0x03\n\t"
+            "vaddss  $tmp2,$tmp2,$tmp\n\t"
+            "vextractf64x2  $tmp3,$src2, 0x3\n\t"
+            "vaddss  $tmp2,$tmp2,$tmp3\n\t"
+            "pshufd  $tmp,$tmp3,0x01\n\t"
+            "vaddss  $tmp2,$tmp2,$tmp\n\t"
+            "pshufd  $tmp,$tmp3,0x02\n\t"
+            "vaddss  $tmp2,$tmp2,$tmp\n\t"
+            "pshufd  $tmp,$tmp3,0x03\n\t"
+            "vaddss  $dst,$tmp2,$tmp\t! add reduction16F" %}
+  ins_encode %{
+    __ vaddss($tmp2$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $src2$$XMMRegister, 0x01);
+    __ vaddss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $src2$$XMMRegister, 0x02);
+    __ vaddss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $src2$$XMMRegister, 0x03);
+    __ vaddss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ vextractf32x4h($tmp3$$XMMRegister, $src2$$XMMRegister, 0x1);
+    __ vaddss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp3$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0x01);
+    __ vaddss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0x02);
+    __ vaddss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0x03);
+    __ vaddss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ vextractf32x4h($tmp3$$XMMRegister, $src2$$XMMRegister, 0x2);
+    __ vaddss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp3$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0x01);
+    __ vaddss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0x02);
+    __ vaddss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0x03);
+    __ vaddss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ vextractf32x4h($tmp3$$XMMRegister, $src2$$XMMRegister, 0x3);
+    __ vaddss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp3$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0x01);
+    __ vaddss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0x02);
+    __ vaddss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0x03);
+    __ vaddss($dst$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
 instruct rsadd2D_reduction_reg(regD dst, regD src1, vecX src2, regD tmp) %{
   predicate(UseSSE >= 1 && UseAVX == 0);
   match(Set dst (AddReductionVD src1 src2));
@@ -2812,6 +4403,45 @@
   ins_pipe( pipe_slow );
 %}
 
+instruct rvadd8D_reduction_reg(regD dst, regD src1, vecZ src2, regD tmp, regD tmp2, regD tmp3) %{
+  predicate(UseAVX > 2);
+  match(Set dst (AddReductionVD src1 src2));
+  effect(TEMP tmp, TEMP tmp2, TEMP tmp3);
+  format %{ "vaddsd  $tmp2,$src1,$src2\n\t"
+            "pshufd  $tmp,$src2,0xE\n\t"
+            "vaddsd  $tmp2,$tmp2,$tmp\n\t"
+            "vextractf64x2  $tmp3,$src2, 0x1\n\t"
+            "vaddsd  $tmp2,$tmp2,$tmp3\n\t"
+            "pshufd  $tmp,$tmp3,0xE\n\t"
+            "vaddsd  $tmp2,$tmp2,$tmp\n\t"
+            "vextractf64x2  $tmp3,$src2, 0x2\n\t"
+            "vaddsd  $tmp2,$tmp2,$tmp3\n\t"
+            "pshufd  $tmp,$tmp3,0xE\n\t"
+            "vaddsd  $tmp2,$tmp2,$tmp\n\t"
+            "vextractf64x2  $tmp3,$src2, 0x3\n\t"
+            "vaddsd  $tmp2,$tmp2,$tmp3\n\t"
+            "pshufd  $tmp,$tmp3,0xE\n\t"
+            "vaddsd  $dst,$tmp2,$tmp\t! add reduction8D" %}
+  ins_encode %{
+    __ vaddsd($tmp2$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $src2$$XMMRegister, 0xE);
+    __ vaddsd($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ vextractf64x2h($tmp3$$XMMRegister, $src2$$XMMRegister, 0x1);
+    __ vaddsd($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp3$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0xE);
+    __ vaddsd($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ vextractf64x2h($tmp3$$XMMRegister, $src2$$XMMRegister, 0x2);
+    __ vaddsd($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp3$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0xE);
+    __ vaddsd($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ vextractf64x2h($tmp3$$XMMRegister, $src2$$XMMRegister, 0x3);
+    __ vaddsd($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp3$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0xE);
+    __ vaddsd($dst$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
 instruct rsmul2I_reduction_reg(rRegI dst, rRegI src1, vecD src2, regF tmp, regF tmp2) %{
   predicate(UseSSE > 3 && UseAVX == 0);
   match(Set dst (MulReductionVI src1 src2));
@@ -2835,16 +4465,17 @@
   predicate(UseAVX > 0);
   match(Set dst (MulReductionVI src1 src2));
   effect(TEMP tmp, TEMP tmp2);
-  format %{ "pshufd  $tmp2,$src2,0x1\n\t"
-            "vpmulld $tmp,$src2,$tmp2\n\t"
-            "movd    $tmp2,$src1\n\t"
-            "vpmulld $tmp2,$tmp,$tmp2\n\t"
-            "movd    $dst,$tmp2\t! mul reduction2I" %}
-  ins_encode %{
+  format %{ "pshufd   $tmp2,$src2,0x1\n\t"
+            "vpmulld  $tmp,$src2,$tmp2\n\t"
+            "movd     $tmp2,$src1\n\t"
+            "vpmulld  $tmp2,$tmp,$tmp2\n\t"
+            "movd     $dst,$tmp2\t! mul reduction2I" %}
+  ins_encode %{
+    int vector_len = 0;
     __ pshufd($tmp2$$XMMRegister, $src2$$XMMRegister, 0x1);
-    __ vpmulld($tmp$$XMMRegister, $src2$$XMMRegister, $tmp2$$XMMRegister, false);
+    __ vpmulld($tmp$$XMMRegister, $src2$$XMMRegister, $tmp2$$XMMRegister, vector_len);
     __ movdl($tmp2$$XMMRegister, $src1$$Register);
-    __ vpmulld($tmp2$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, false);
+    __ vpmulld($tmp2$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, vector_len);
     __ movdl($dst$$Register, $tmp2$$XMMRegister);
   %}
   ins_pipe( pipe_slow );
@@ -2877,20 +4508,21 @@
   predicate(UseAVX > 0);
   match(Set dst (MulReductionVI src1 src2));
   effect(TEMP tmp, TEMP tmp2);
-  format %{ "pshufd  $tmp2,$src2,0xE\n\t"
-            "vpmulld $tmp,$src2,$tmp2\n\t"
-            "pshufd  $tmp2,$tmp,0x1\n\t"
-            "vpmulld $tmp,$tmp,$tmp2\n\t"
-            "movd    $tmp2,$src1\n\t"
-            "vpmulld $tmp2,$tmp,$tmp2\n\t"
-            "movd    $dst,$tmp2\t! mul reduction4I" %}
-  ins_encode %{
+  format %{ "pshufd   $tmp2,$src2,0xE\n\t"
+            "vpmulld  $tmp,$src2,$tmp2\n\t"
+            "pshufd   $tmp2,$tmp,0x1\n\t"
+            "vpmulld  $tmp,$tmp,$tmp2\n\t"
+            "movd     $tmp2,$src1\n\t"
+            "vpmulld  $tmp2,$tmp,$tmp2\n\t"
+            "movd     $dst,$tmp2\t! mul reduction4I" %}
+  ins_encode %{
+    int vector_len = 0;
     __ pshufd($tmp2$$XMMRegister, $src2$$XMMRegister, 0xE);
-    __ vpmulld($tmp$$XMMRegister, $src2$$XMMRegister, $tmp2$$XMMRegister, false);
+    __ vpmulld($tmp$$XMMRegister, $src2$$XMMRegister, $tmp2$$XMMRegister, vector_len);
     __ pshufd($tmp2$$XMMRegister, $tmp$$XMMRegister, 0x1);
-    __ vpmulld($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, false);
+    __ vpmulld($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, vector_len);
     __ movdl($tmp2$$XMMRegister, $src1$$Register);
-    __ vpmulld($tmp2$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, false);
+    __ vpmulld($tmp2$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, vector_len);
     __ movdl($dst$$Register, $tmp2$$XMMRegister);
   %}
   ins_pipe( pipe_slow );
@@ -2900,30 +4532,133 @@
   predicate(UseAVX > 0);
   match(Set dst (MulReductionVI src1 src2));
   effect(TEMP tmp, TEMP tmp2);
-  format %{ "vextractf128  $tmp,$src2\n\t"
-            "vpmulld $tmp,$tmp,$src2\n\t"
-            "pshufd  $tmp2,$tmp,0xE\n\t"
-            "vpmulld $tmp,$tmp,$tmp2\n\t"
-            "pshufd  $tmp2,$tmp,0x1\n\t"
-            "vpmulld $tmp,$tmp,$tmp2\n\t"
-            "movd    $tmp2,$src1\n\t"
-            "vpmulld $tmp2,$tmp,$tmp2\n\t"
-            "movd    $dst,$tmp2\t! mul reduction8I" %}
-  ins_encode %{
-    __ vextractf128h($tmp$$XMMRegister, $src2$$XMMRegister);
-    __ vpmulld($tmp$$XMMRegister, $tmp$$XMMRegister, $src2$$XMMRegister, false);
+  format %{ "vextracti128  $tmp,$src2\n\t"
+            "vpmulld  $tmp,$tmp,$src2\n\t"
+            "pshufd   $tmp2,$tmp,0xE\n\t"
+            "vpmulld  $tmp,$tmp,$tmp2\n\t"
+            "pshufd   $tmp2,$tmp,0x1\n\t"
+            "vpmulld  $tmp,$tmp,$tmp2\n\t"
+            "movd     $tmp2,$src1\n\t"
+            "vpmulld  $tmp2,$tmp,$tmp2\n\t"
+            "movd     $dst,$tmp2\t! mul reduction8I" %}
+  ins_encode %{
+    int vector_len = 0;
+    __ vextracti128h($tmp$$XMMRegister, $src2$$XMMRegister);
+    __ vpmulld($tmp$$XMMRegister, $tmp$$XMMRegister, $src2$$XMMRegister, vector_len);
+    __ pshufd($tmp2$$XMMRegister, $tmp$$XMMRegister, 0xE);
+    __ vpmulld($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, vector_len);
+    __ pshufd($tmp2$$XMMRegister, $tmp$$XMMRegister, 0x1);
+    __ vpmulld($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, vector_len);
+    __ movdl($tmp2$$XMMRegister, $src1$$Register);
+    __ vpmulld($tmp2$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, vector_len);
+    __ movdl($dst$$Register, $tmp2$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct rvmul16I_reduction_reg(rRegI dst, rRegI src1, vecZ src2, regF tmp, regF tmp2, regF tmp3) %{
+  predicate(UseAVX > 2);
+  match(Set dst (MulReductionVI src1 src2));
+  effect(TEMP tmp, TEMP tmp2, TEMP tmp3);
+  format %{ "vextracti64x4  $tmp3,$src2\n\t"
+            "vpmulld  $tmp3,$tmp3,$src2\n\t"
+            "vextracti128   $tmp,$tmp3\n\t"
+            "vpmulld  $tmp,$tmp,$src2\n\t"
+            "pshufd   $tmp2,$tmp,0xE\n\t"
+            "vpmulld  $tmp,$tmp,$tmp2\n\t"
+            "pshufd   $tmp2,$tmp,0x1\n\t"
+            "vpmulld  $tmp,$tmp,$tmp2\n\t"
+            "movd     $tmp2,$src1\n\t"
+            "vpmulld  $tmp2,$tmp,$tmp2\n\t"
+            "movd     $dst,$tmp2\t! mul reduction16I" %}
+  ins_encode %{
+    __ vextracti64x4h($tmp3$$XMMRegister, $src2$$XMMRegister);
+    __ vpmulld($tmp3$$XMMRegister, $tmp3$$XMMRegister, $src2$$XMMRegister, 1);
+    __ vextracti128h($tmp$$XMMRegister, $tmp3$$XMMRegister);
+    __ vpmulld($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp3$$XMMRegister, 0);
     __ pshufd($tmp2$$XMMRegister, $tmp$$XMMRegister, 0xE);
-    __ vpmulld($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, false);
+    __ vpmulld($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, 0);
     __ pshufd($tmp2$$XMMRegister, $tmp$$XMMRegister, 0x1);
-    __ vpmulld($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, false);
+    __ vpmulld($tmp$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, 0);
     __ movdl($tmp2$$XMMRegister, $src1$$Register);
-    __ vpmulld($tmp2$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, false);
+    __ vpmulld($tmp2$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, 0);
     __ movdl($dst$$Register, $tmp2$$XMMRegister);
   %}
   ins_pipe( pipe_slow );
 %}
 
-instruct rsmul2F_reduction_reg(regF dst, regF src1, vecD src2, regF tmp, regF tmp2) %{
+#ifdef _LP64
+instruct rvmul2L_reduction_reg(rRegL dst, rRegL src1, vecX src2, regF tmp, regF tmp2) %{
+  predicate(UseAVX > 2 && VM_Version::supports_avx512dq());
+  match(Set dst (MulReductionVL src1 src2));
+  effect(TEMP tmp, TEMP tmp2);
+  format %{ "pshufd   $tmp2,$src2,0xE\n\t"
+            "vpmullq  $tmp,$src2,$tmp2\n\t"
+            "movdq    $tmp2,$src1\n\t"
+            "vpmullq  $tmp2,$tmp,$tmp2\n\t"
+            "movdq    $dst,$tmp2\t! mul reduction2L" %}
+  ins_encode %{
+    __ pshufd($tmp2$$XMMRegister, $src2$$XMMRegister, 0xE);
+    __ vpmullq($tmp$$XMMRegister, $src2$$XMMRegister, $tmp2$$XMMRegister, 0);
+    __ movdq($tmp2$$XMMRegister, $src1$$Register);
+    __ vpmullq($tmp2$$XMMRegister, $tmp$$XMMRegister, $tmp2$$XMMRegister, 0);
+    __ movdq($dst$$Register, $tmp2$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct rvmul4L_reduction_reg(rRegL dst, rRegL src1, vecY src2, regF tmp, regF tmp2) %{
+  predicate(UseAVX > 2 && VM_Version::supports_avx512dq());
+  match(Set dst (MulReductionVL src1 src2));
+  effect(TEMP tmp, TEMP tmp2);
+  format %{ "vextracti64x2  $tmp,$src2, 0x1\n\t"
+            "vpmullq  $tmp2,$tmp,$src2\n\t"
+            "pshufd   $tmp,$tmp2,0xE\n\t"
+            "vpmullq  $tmp2,$tmp2,$tmp\n\t"
+            "movdq    $tmp,$src1\n\t"
+            "vpmullq  $tmp2,$tmp2,$tmp\n\t"
+            "movdq    $dst,$tmp2\t! mul reduction4L" %}
+  ins_encode %{
+    __ vextracti64x2h($tmp$$XMMRegister, $src2$$XMMRegister, 0x1);
+    __ vpmullq($tmp2$$XMMRegister, $tmp$$XMMRegister, $src2$$XMMRegister, 0);
+    __ pshufd($tmp$$XMMRegister, $tmp2$$XMMRegister, 0xE);
+    __ vpmullq($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister, 0);
+    __ movdq($tmp$$XMMRegister, $src1$$Register);
+    __ vpmullq($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister, 0);
+    __ movdq($dst$$Register, $tmp2$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct rvmul8L_reduction_reg(rRegL dst, rRegL src1, vecZ src2, regF tmp, regF tmp2) %{
+  predicate(UseAVX > 2 && VM_Version::supports_avx512dq());
+  match(Set dst (MulReductionVL src1 src2));
+  effect(TEMP tmp, TEMP tmp2);
+  format %{ "vextracti64x4  $tmp2,$src2\n\t"
+            "vpmullq  $tmp2,$tmp2,$src2\n\t"
+            "vextracti128   $tmp,$tmp2\n\t"
+            "vpmullq  $tmp2,$tmp2,$tmp\n\t"
+            "pshufd   $tmp,$tmp2,0xE\n\t"
+            "vpmullq  $tmp2,$tmp2,$tmp\n\t"
+            "movdq    $tmp,$src1\n\t"
+            "vpmullq  $tmp2,$tmp2,$tmp\n\t"
+            "movdq    $dst,$tmp2\t! mul reduction8L" %}
+  ins_encode %{
+    __ vextracti64x4h($tmp2$$XMMRegister, $src2$$XMMRegister);
+    __ vpmullq($tmp2$$XMMRegister, $tmp2$$XMMRegister, $src2$$XMMRegister, 1);
+    __ vextracti128h($tmp$$XMMRegister, $tmp2$$XMMRegister);
+    __ vpmullq($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister, 0);
+    __ pshufd($tmp$$XMMRegister, $tmp2$$XMMRegister, 0xE);
+    __ vpmullq($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister, 0);
+    __ movdq($tmp$$XMMRegister, $src1$$Register);
+    __ vpmullq($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister, 0);
+    __ movdq($dst$$Register, $tmp2$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+#endif
+
+instruct rsmul2F_reduction(regF dst, regF src1, vecD src2, regF tmp, regF tmp2) %{
   predicate(UseSSE >= 1 && UseAVX == 0);
   match(Set dst (MulReductionVF src1 src2));
   effect(TEMP tmp, TEMP tmp2);
@@ -2931,7 +4666,7 @@
             "mulss   $tmp,$src2\n\t"
             "pshufd  $tmp2,$src2,0x01\n\t"
             "mulss   $tmp,$tmp2\n\t"
-            "movdqu  $dst,$tmp\t! add reduction2F" %}
+            "movdqu  $dst,$tmp\t! mul reduction2F" %}
   ins_encode %{
     __ movdqu($tmp$$XMMRegister, $src1$$XMMRegister);
     __ mulss($tmp$$XMMRegister, $src2$$XMMRegister);
@@ -2948,7 +4683,7 @@
   effect(TEMP tmp, TEMP tmp2);
   format %{ "vmulss  $tmp2,$src1,$src2\n\t"
             "pshufd  $tmp,$src2,0x01\n\t"
-            "vmulss  $dst,$tmp2,$tmp\t! add reduction2F" %}
+            "vmulss  $dst,$tmp2,$tmp\t! mul reduction2F" %}
   ins_encode %{
     __ vmulss($tmp2$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister);
     __ pshufd($tmp$$XMMRegister, $src2$$XMMRegister, 0x01);
@@ -2969,7 +4704,7 @@
             "mulss   $tmp,$tmp2\n\t"
             "pshufd  $tmp2,$src2,0x03\n\t"
             "mulss   $tmp,$tmp2\n\t"
-            "movdqu  $dst,$tmp\t! add reduction4F" %}
+            "movdqu  $dst,$tmp\t! mul reduction4F" %}
   ins_encode %{
     __ movdqu($tmp$$XMMRegister, $src1$$XMMRegister);
     __ mulss($tmp$$XMMRegister, $src2$$XMMRegister);
@@ -2994,7 +4729,7 @@
             "pshufd  $tmp,$src2,0x02\n\t"
             "vmulss  $tmp2,$tmp2,$tmp\n\t"
             "pshufd  $tmp,$src2,0x03\n\t"
-            "vmulss  $dst,$tmp2,$tmp\t! add reduction4F" %}
+            "vmulss  $dst,$tmp2,$tmp\t! mul reduction4F" %}
   ins_encode %{
     __ vmulss($tmp2$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister);
     __ pshufd($tmp$$XMMRegister, $src2$$XMMRegister, 0x01);
@@ -3046,6 +4781,77 @@
   ins_pipe( pipe_slow );
 %}
 
+instruct rvmul16F_reduction_reg(regF dst, regF src1, vecZ src2, regF tmp, regF tmp2, regF tmp3) %{
+  predicate(UseAVX > 2);
+  match(Set dst (MulReductionVF src1 src2));
+  effect(TEMP tmp, TEMP tmp2, TEMP tmp3);
+  format %{ "vmulss  $tmp2,$src1,$src2\n\t"
+            "pshufd  $tmp,$src2,0x01\n\t"
+            "vmulss  $tmp2,$tmp2,$tmp\n\t"
+            "pshufd  $tmp,$src2,0x02\n\t"
+            "vmulss  $tmp2,$tmp2,$tmp\n\t"
+            "pshufd  $tmp,$src2,0x03\n\t"
+            "vmulss  $tmp2,$tmp2,$tmp\n\t"
+            "vextractf32x4  $tmp3,$src2, 0x1\n\t"
+            "vmulss  $tmp2,$tmp2,$tmp3\n\t"
+            "pshufd  $tmp,$tmp3,0x01\n\t"
+            "vmulss  $tmp2,$tmp2,$tmp\n\t"
+            "pshufd  $tmp,$tmp3,0x02\n\t"
+            "vmulss  $tmp2,$tmp2,$tmp\n\t"
+            "pshufd  $tmp,$tmp3,0x03\n\t"
+            "vmulss  $tmp2,$tmp2,$tmp\n\t"
+            "vextractf32x4  $tmp3,$src2, 0x2\n\t"
+            "vmulss  $tmp2,$tmp2,$tmp3\n\t"
+            "pshufd  $tmp,$tmp3,0x01\n\t"
+            "vmulss  $tmp2,$tmp2,$tmp\n\t"
+            "pshufd  $tmp,$tmp3,0x02\n\t"
+            "vmulss  $tmp2,$tmp2,$tmp\n\t"
+            "pshufd  $tmp,$tmp3,0x03\n\t"
+            "vmulss  $tmp2,$tmp2,$tmp\n\t"
+            "vextractf32x4  $tmp3,$src2, 0x3\n\t"
+            "vmulss  $tmp2,$tmp2,$tmp3\n\t"
+            "pshufd  $tmp,$tmp3,0x01\n\t"
+            "vmulss  $tmp2,$tmp2,$tmp\n\t"
+            "pshufd  $tmp,$tmp3,0x02\n\t"
+            "vmulss  $tmp2,$tmp2,$tmp\n\t"
+            "pshufd  $tmp,$tmp3,0x03\n\t"
+            "vmulss  $dst,$tmp2,$tmp\t! mul reduction16F" %}
+  ins_encode %{
+    __ vmulss($tmp2$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $src2$$XMMRegister, 0x01);
+    __ vmulss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $src2$$XMMRegister, 0x02);
+    __ vmulss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $src2$$XMMRegister, 0x03);
+    __ vmulss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ vextractf32x4h($tmp3$$XMMRegister, $src2$$XMMRegister, 0x1);
+    __ vmulss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp3$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0x01);
+    __ vmulss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0x02);
+    __ vmulss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0x03);
+    __ vmulss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ vextractf32x4h($tmp3$$XMMRegister, $src2$$XMMRegister, 0x2);
+    __ vmulss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp3$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0x01);
+    __ vmulss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0x02);
+    __ vmulss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0x03);
+    __ vmulss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ vextractf32x4h($tmp3$$XMMRegister, $src2$$XMMRegister, 0x3);
+    __ vmulss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp3$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0x01);
+    __ vmulss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0x02);
+    __ vmulss($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0x03);
+    __ vmulss($dst$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
 instruct rsmul2D_reduction_reg(regD dst, regD src1, vecX src2, regD tmp) %{
   predicate(UseSSE >= 1 && UseAVX == 0);
   match(Set dst (MulReductionVD src1 src2));
@@ -3053,7 +4859,7 @@
   format %{ "movdqu  $tmp,$src1\n\t"
             "mulsd   $tmp,$src2\n\t"
             "pshufd  $dst,$src2,0xE\n\t"
-            "mulsd   $dst,$tmp\t! add reduction2D" %}
+            "mulsd   $dst,$tmp\t! mul reduction2D" %}
   ins_encode %{
     __ movdqu($tmp$$XMMRegister, $src1$$XMMRegister);
     __ mulsd($tmp$$XMMRegister, $src2$$XMMRegister);
@@ -3101,6 +4907,45 @@
   ins_pipe( pipe_slow );
 %}
 
+instruct rvmul8D_reduction_reg(regD dst, regD src1, vecZ src2, regD tmp, regD tmp2, regD tmp3) %{
+  predicate(UseAVX > 2);
+  match(Set dst (MulReductionVD src1 src2));
+  effect(TEMP tmp, TEMP tmp2, TEMP tmp3);
+  format %{ "vmulsd  $tmp2,$src1,$src2\n\t"
+            "pshufd  $tmp,$src2,0xE\n\t"
+            "vmulsd  $tmp2,$tmp2,$tmp\n\t"
+            "vextractf64x2  $tmp3,$src2, 0x1\n\t"
+            "vmulsd  $tmp2,$tmp2,$tmp3\n\t"
+            "pshufd  $tmp,$src2,0xE\n\t"
+            "vmulsd  $tmp2,$tmp2,$tmp\n\t"
+            "vextractf64x2  $tmp3,$src2, 0x2\n\t"
+            "vmulsd  $tmp2,$tmp2,$tmp3\n\t"
+            "pshufd  $tmp,$tmp3,0xE\n\t"
+            "vmulsd  $tmp2,$tmp2,$tmp\n\t"
+            "vextractf64x2  $tmp3,$src2, 0x3\n\t"
+            "vmulsd  $tmp2,$tmp2,$tmp3\n\t"
+            "pshufd  $tmp,$tmp3,0xE\n\t"
+            "vmulsd  $dst,$tmp2,$tmp\t! mul reduction8D" %}
+  ins_encode %{
+    __ vmulsd($tmp2$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $src2$$XMMRegister, 0xE);
+    __ vmulsd($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ vextractf64x2h($tmp3$$XMMRegister, $src2$$XMMRegister, 0x1);
+    __ vmulsd($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp3$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0xE);
+    __ vmulsd($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ vextractf64x2h($tmp3$$XMMRegister, $src2$$XMMRegister, 0x2);
+    __ vmulsd($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp3$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0xE);
+    __ vmulsd($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+    __ vextractf64x2h($tmp3$$XMMRegister, $src2$$XMMRegister, 0x3);
+    __ vmulsd($tmp2$$XMMRegister, $tmp2$$XMMRegister, $tmp3$$XMMRegister);
+    __ pshufd($tmp$$XMMRegister, $tmp3$$XMMRegister, 0xE);
+    __ vmulsd($dst$$XMMRegister, $tmp2$$XMMRegister, $tmp$$XMMRegister);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
 // ====================VECTOR ARITHMETIC=======================================
 
 // --------------------------------- ADD --------------------------------------
@@ -3121,8 +4966,8 @@
   match(Set dst (AddVB src1 src2));
   format %{ "vpaddb  $dst,$src1,$src2\t! add packed4B" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpaddb($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpaddb($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3142,8 +4987,8 @@
   match(Set dst (AddVB src1 src2));
   format %{ "vpaddb  $dst,$src1,$src2\t! add packed8B" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpaddb($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpaddb($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3163,8 +5008,8 @@
   match(Set dst (AddVB src1 src2));
   format %{ "vpaddb  $dst,$src1,$src2\t! add packed16B" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpaddb($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpaddb($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3174,8 +5019,8 @@
   match(Set dst (AddVB src (LoadVector mem)));
   format %{ "vpaddb  $dst,$src,$mem\t! add packed16B" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpaddb($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vpaddb($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3185,8 +5030,8 @@
   match(Set dst (AddVB src1 src2));
   format %{ "vpaddb  $dst,$src1,$src2\t! add packed32B" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpaddb($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpaddb($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3196,8 +5041,30 @@
   match(Set dst (AddVB src (LoadVector mem)));
   format %{ "vpaddb  $dst,$src,$mem\t! add packed32B" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpaddb($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 1;
+    __ vpaddb($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vadd64B_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 64);
+  match(Set dst (AddVB src1 src2));
+  format %{ "vpaddb  $dst,$src1,$src2\t! add packed64B" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpaddb($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vadd64B_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 64);
+  match(Set dst (AddVB src (LoadVector mem)));
+  format %{ "vpaddb  $dst,$src,$mem\t! add packed64B" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpaddb($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3218,8 +5085,8 @@
   match(Set dst (AddVS src1 src2));
   format %{ "vpaddw  $dst,$src1,$src2\t! add packed2S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpaddw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpaddw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3239,8 +5106,8 @@
   match(Set dst (AddVS src1 src2));
   format %{ "vpaddw  $dst,$src1,$src2\t! add packed4S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpaddw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpaddw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3260,8 +5127,8 @@
   match(Set dst (AddVS src1 src2));
   format %{ "vpaddw  $dst,$src1,$src2\t! add packed8S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpaddw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpaddw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3271,8 +5138,8 @@
   match(Set dst (AddVS src (LoadVector mem)));
   format %{ "vpaddw  $dst,$src,$mem\t! add packed8S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpaddw($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vpaddw($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3282,8 +5149,8 @@
   match(Set dst (AddVS src1 src2));
   format %{ "vpaddw  $dst,$src1,$src2\t! add packed16S" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpaddw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpaddw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3293,8 +5160,30 @@
   match(Set dst (AddVS src (LoadVector mem)));
   format %{ "vpaddw  $dst,$src,$mem\t! add packed16S" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpaddw($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 1;
+    __ vpaddw($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vadd32S_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 32);
+  match(Set dst (AddVS src1 src2));
+  format %{ "vpaddw  $dst,$src1,$src2\t! add packed32S" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpaddw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vadd32S_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 32);
+  match(Set dst (AddVS src (LoadVector mem)));
+  format %{ "vpaddw  $dst,$src,$mem\t! add packed32S" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpaddw($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3315,8 +5204,8 @@
   match(Set dst (AddVI src1 src2));
   format %{ "vpaddd  $dst,$src1,$src2\t! add packed2I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpaddd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpaddd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3336,8 +5225,8 @@
   match(Set dst (AddVI src1 src2));
   format %{ "vpaddd  $dst,$src1,$src2\t! add packed4I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpaddd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpaddd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3347,8 +5236,8 @@
   match(Set dst (AddVI src (LoadVector mem)));
   format %{ "vpaddd  $dst,$src,$mem\t! add packed4I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpaddd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vpaddd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3358,8 +5247,8 @@
   match(Set dst (AddVI src1 src2));
   format %{ "vpaddd  $dst,$src1,$src2\t! add packed8I" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpaddd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpaddd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3369,8 +5258,30 @@
   match(Set dst (AddVI src (LoadVector mem)));
   format %{ "vpaddd  $dst,$src,$mem\t! add packed8I" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpaddd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 1;
+    __ vpaddd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vadd16I_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 16);
+  match(Set dst (AddVI src1 src2));
+  format %{ "vpaddd  $dst,$src1,$src2\t! add packed16I" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpaddd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vadd16I_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 16);
+  match(Set dst (AddVI src (LoadVector mem)));
+  format %{ "vpaddd  $dst,$src,$mem\t! add packed16I" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpaddd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3391,8 +5302,8 @@
   match(Set dst (AddVL src1 src2));
   format %{ "vpaddq  $dst,$src1,$src2\t! add packed2L" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpaddq($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpaddq($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3402,8 +5313,8 @@
   match(Set dst (AddVL src (LoadVector mem)));
   format %{ "vpaddq  $dst,$src,$mem\t! add packed2L" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpaddq($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vpaddq($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3413,8 +5324,8 @@
   match(Set dst (AddVL src1 src2));
   format %{ "vpaddq  $dst,$src1,$src2\t! add packed4L" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpaddq($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpaddq($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3424,8 +5335,30 @@
   match(Set dst (AddVL src (LoadVector mem)));
   format %{ "vpaddq  $dst,$src,$mem\t! add packed4L" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpaddq($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 1;
+    __ vpaddq($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vadd8L_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 8);
+  match(Set dst (AddVL src1 src2));
+  format %{ "vpaddq  $dst,$src1,$src2\t! add packed8L" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpaddq($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vadd8L_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 8);
+  match(Set dst (AddVL src (LoadVector mem)));
+  format %{ "vpaddq  $dst,$src,$mem\t! add packed8L" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpaddq($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3446,8 +5379,8 @@
   match(Set dst (AddVF src1 src2));
   format %{ "vaddps  $dst,$src1,$src2\t! add packed2F" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vaddps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vaddps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3467,8 +5400,8 @@
   match(Set dst (AddVF src1 src2));
   format %{ "vaddps  $dst,$src1,$src2\t! add packed4F" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vaddps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vaddps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3478,8 +5411,8 @@
   match(Set dst (AddVF src (LoadVector mem)));
   format %{ "vaddps  $dst,$src,$mem\t! add packed4F" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vaddps($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vaddps($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3489,8 +5422,8 @@
   match(Set dst (AddVF src1 src2));
   format %{ "vaddps  $dst,$src1,$src2\t! add packed8F" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vaddps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vaddps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3500,8 +5433,30 @@
   match(Set dst (AddVF src (LoadVector mem)));
   format %{ "vaddps  $dst,$src,$mem\t! add packed8F" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vaddps($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 1;
+    __ vaddps($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vadd16F_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 16);
+  match(Set dst (AddVF src1 src2));
+  format %{ "vaddps  $dst,$src1,$src2\t! add packed16F" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vaddps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vadd16F_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 16);
+  match(Set dst (AddVF src (LoadVector mem)));
+  format %{ "vaddps  $dst,$src,$mem\t! add packed16F" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vaddps($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3522,8 +5477,8 @@
   match(Set dst (AddVD src1 src2));
   format %{ "vaddpd  $dst,$src1,$src2\t! add packed2D" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vaddpd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vaddpd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3533,8 +5488,8 @@
   match(Set dst (AddVD src (LoadVector mem)));
   format %{ "vaddpd  $dst,$src,$mem\t! add packed2D" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vaddpd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vaddpd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3544,8 +5499,8 @@
   match(Set dst (AddVD src1 src2));
   format %{ "vaddpd  $dst,$src1,$src2\t! add packed4D" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vaddpd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vaddpd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3555,8 +5510,30 @@
   match(Set dst (AddVD src (LoadVector mem)));
   format %{ "vaddpd  $dst,$src,$mem\t! add packed4D" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vaddpd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 1;
+    __ vaddpd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vadd8D_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 8);
+  match(Set dst (AddVD src1 src2));
+  format %{ "vaddpd  $dst,$src1,$src2\t! add packed8D" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vaddpd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vadd8D_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 8);
+  match(Set dst (AddVD src (LoadVector mem)));
+  format %{ "vaddpd  $dst,$src,$mem\t! add packed8D" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vaddpd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3579,8 +5556,8 @@
   match(Set dst (SubVB src1 src2));
   format %{ "vpsubb  $dst,$src1,$src2\t! sub packed4B" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsubb($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsubb($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3600,8 +5577,8 @@
   match(Set dst (SubVB src1 src2));
   format %{ "vpsubb  $dst,$src1,$src2\t! sub packed8B" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsubb($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsubb($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3621,8 +5598,8 @@
   match(Set dst (SubVB src1 src2));
   format %{ "vpsubb  $dst,$src1,$src2\t! sub packed16B" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsubb($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsubb($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3632,8 +5609,8 @@
   match(Set dst (SubVB src (LoadVector mem)));
   format %{ "vpsubb  $dst,$src,$mem\t! sub packed16B" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsubb($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vpsubb($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3643,8 +5620,8 @@
   match(Set dst (SubVB src1 src2));
   format %{ "vpsubb  $dst,$src1,$src2\t! sub packed32B" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsubb($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpsubb($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3654,8 +5631,30 @@
   match(Set dst (SubVB src (LoadVector mem)));
   format %{ "vpsubb  $dst,$src,$mem\t! sub packed32B" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsubb($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 1;
+    __ vpsubb($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsub64B_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 64);
+  match(Set dst (SubVB src1 src2));
+  format %{ "vpsubb  $dst,$src1,$src2\t! sub packed64B" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsubb($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsub64B_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 64);
+  match(Set dst (SubVB src (LoadVector mem)));
+  format %{ "vpsubb  $dst,$src,$mem\t! sub packed64B" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsubb($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3676,8 +5675,8 @@
   match(Set dst (SubVS src1 src2));
   format %{ "vpsubw  $dst,$src1,$src2\t! sub packed2S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsubw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsubw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3697,8 +5696,8 @@
   match(Set dst (SubVS src1 src2));
   format %{ "vpsubw  $dst,$src1,$src2\t! sub packed4S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsubw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsubw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3718,8 +5717,8 @@
   match(Set dst (SubVS src1 src2));
   format %{ "vpsubw  $dst,$src1,$src2\t! sub packed8S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsubw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsubw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3729,8 +5728,8 @@
   match(Set dst (SubVS src (LoadVector mem)));
   format %{ "vpsubw  $dst,$src,$mem\t! sub packed8S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsubw($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vpsubw($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3740,8 +5739,8 @@
   match(Set dst (SubVS src1 src2));
   format %{ "vpsubw  $dst,$src1,$src2\t! sub packed16S" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsubw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpsubw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3751,8 +5750,30 @@
   match(Set dst (SubVS src (LoadVector mem)));
   format %{ "vpsubw  $dst,$src,$mem\t! sub packed16S" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsubw($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 1;
+    __ vpsubw($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsub32S_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 32);
+  match(Set dst (SubVS src1 src2));
+  format %{ "vpsubw  $dst,$src1,$src2\t! sub packed32S" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsubw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsub32S_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 32);
+  match(Set dst (SubVS src (LoadVector mem)));
+  format %{ "vpsubw  $dst,$src,$mem\t! sub packed32S" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsubw($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3773,8 +5794,8 @@
   match(Set dst (SubVI src1 src2));
   format %{ "vpsubd  $dst,$src1,$src2\t! sub packed2I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsubd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsubd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3794,8 +5815,8 @@
   match(Set dst (SubVI src1 src2));
   format %{ "vpsubd  $dst,$src1,$src2\t! sub packed4I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsubd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsubd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3805,8 +5826,8 @@
   match(Set dst (SubVI src (LoadVector mem)));
   format %{ "vpsubd  $dst,$src,$mem\t! sub packed4I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsubd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vpsubd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3816,8 +5837,8 @@
   match(Set dst (SubVI src1 src2));
   format %{ "vpsubd  $dst,$src1,$src2\t! sub packed8I" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsubd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpsubd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3827,8 +5848,30 @@
   match(Set dst (SubVI src (LoadVector mem)));
   format %{ "vpsubd  $dst,$src,$mem\t! sub packed8I" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsubd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 1;
+    __ vpsubd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsub16I_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 16);
+  match(Set dst (SubVI src1 src2));
+  format %{ "vpsubd  $dst,$src1,$src2\t! sub packed16I" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsubd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsub16I_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 16);
+  match(Set dst (SubVI src (LoadVector mem)));
+  format %{ "vpsubd  $dst,$src,$mem\t! sub packed16I" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsubd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3849,8 +5892,8 @@
   match(Set dst (SubVL src1 src2));
   format %{ "vpsubq  $dst,$src1,$src2\t! sub packed2L" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsubq($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsubq($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3860,8 +5903,8 @@
   match(Set dst (SubVL src (LoadVector mem)));
   format %{ "vpsubq  $dst,$src,$mem\t! sub packed2L" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsubq($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vpsubq($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3871,8 +5914,8 @@
   match(Set dst (SubVL src1 src2));
   format %{ "vpsubq  $dst,$src1,$src2\t! sub packed4L" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsubq($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpsubq($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3882,8 +5925,30 @@
   match(Set dst (SubVL src (LoadVector mem)));
   format %{ "vpsubq  $dst,$src,$mem\t! sub packed4L" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsubq($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 1;
+    __ vpsubq($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsub8L_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 8);
+  match(Set dst (SubVL src1 src2));
+  format %{ "vpsubq  $dst,$src1,$src2\t! sub packed8L" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsubq($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsub8L_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 8);
+  match(Set dst (SubVL src (LoadVector mem)));
+  format %{ "vpsubq  $dst,$src,$mem\t! sub packed8L" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsubq($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3904,8 +5969,8 @@
   match(Set dst (SubVF src1 src2));
   format %{ "vsubps  $dst,$src1,$src2\t! sub packed2F" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vsubps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vsubps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3925,8 +5990,8 @@
   match(Set dst (SubVF src1 src2));
   format %{ "vsubps  $dst,$src1,$src2\t! sub packed4F" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vsubps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vsubps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3936,8 +6001,8 @@
   match(Set dst (SubVF src (LoadVector mem)));
   format %{ "vsubps  $dst,$src,$mem\t! sub packed4F" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vsubps($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vsubps($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3947,8 +6012,8 @@
   match(Set dst (SubVF src1 src2));
   format %{ "vsubps  $dst,$src1,$src2\t! sub packed8F" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vsubps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vsubps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3958,8 +6023,30 @@
   match(Set dst (SubVF src (LoadVector mem)));
   format %{ "vsubps  $dst,$src,$mem\t! sub packed8F" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vsubps($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 1;
+    __ vsubps($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsub16F_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 16);
+  match(Set dst (SubVF src1 src2));
+  format %{ "vsubps  $dst,$src1,$src2\t! sub packed16F" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vsubps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsub16F_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 16);
+  match(Set dst (SubVF src (LoadVector mem)));
+  format %{ "vsubps  $dst,$src,$mem\t! sub packed16F" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vsubps($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3980,8 +6067,8 @@
   match(Set dst (SubVD src1 src2));
   format %{ "vsubpd  $dst,$src1,$src2\t! sub packed2D" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vsubpd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vsubpd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -3991,8 +6078,8 @@
   match(Set dst (SubVD src (LoadVector mem)));
   format %{ "vsubpd  $dst,$src,$mem\t! sub packed2D" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vsubpd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vsubpd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4002,8 +6089,8 @@
   match(Set dst (SubVD src1 src2));
   format %{ "vsubpd  $dst,$src1,$src2\t! sub packed4D" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vsubpd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vsubpd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4013,8 +6100,30 @@
   match(Set dst (SubVD src (LoadVector mem)));
   format %{ "vsubpd  $dst,$src,$mem\t! sub packed4D" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vsubpd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 1;
+    __ vsubpd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsub8D_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 8);
+  match(Set dst (SubVD src1 src2));
+  format %{ "vsubpd  $dst,$src1,$src2\t! sub packed8D" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vsubpd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsub8D_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 8);
+  match(Set dst (SubVD src (LoadVector mem)));
+  format %{ "vsubpd  $dst,$src,$mem\t! sub packed8D" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vsubpd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4037,8 +6146,8 @@
   match(Set dst (MulVS src1 src2));
   format %{ "vpmullw $dst,$src1,$src2\t! mul packed2S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpmullw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpmullw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4058,8 +6167,8 @@
   match(Set dst (MulVS src1 src2));
   format %{ "vpmullw $dst,$src1,$src2\t! mul packed4S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpmullw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpmullw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4079,8 +6188,8 @@
   match(Set dst (MulVS src1 src2));
   format %{ "vpmullw $dst,$src1,$src2\t! mul packed8S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpmullw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpmullw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4090,8 +6199,8 @@
   match(Set dst (MulVS src (LoadVector mem)));
   format %{ "vpmullw $dst,$src,$mem\t! mul packed8S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpmullw($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vpmullw($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4101,8 +6210,8 @@
   match(Set dst (MulVS src1 src2));
   format %{ "vpmullw $dst,$src1,$src2\t! mul packed16S" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpmullw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpmullw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4112,8 +6221,30 @@
   match(Set dst (MulVS src (LoadVector mem)));
   format %{ "vpmullw $dst,$src,$mem\t! mul packed16S" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpmullw($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 1;
+    __ vpmullw($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vmul32S_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 32);
+  match(Set dst (MulVS src1 src2));
+  format %{ "vpmullw $dst,$src1,$src2\t! mul packed32S" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpmullw($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vmul32S_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 32);
+  match(Set dst (MulVS src (LoadVector mem)));
+  format %{ "vpmullw $dst,$src,$mem\t! mul packed32S" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpmullw($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4134,8 +6265,19 @@
   match(Set dst (MulVI src1 src2));
   format %{ "vpmulld $dst,$src1,$src2\t! mul packed2I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpmulld($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpmulld($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vmul2L_reg(vecX dst, vecX src1, vecX src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 2 && VM_Version::supports_avx512dq());
+  match(Set dst (MulVL src1 src2));
+  format %{ "vpmullq $dst,$src1,$src2\t! mul packed2L" %}
+  ins_encode %{
+    int vector_len = 0;
+    __ vpmullq($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4155,8 +6297,8 @@
   match(Set dst (MulVI src1 src2));
   format %{ "vpmulld $dst,$src1,$src2\t! mul packed4I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpmulld($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpmulld($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4166,8 +6308,30 @@
   match(Set dst (MulVI src (LoadVector mem)));
   format %{ "vpmulld $dst,$src,$mem\t! mul packed4I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpmulld($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vpmulld($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vmul4L_reg(vecY dst, vecY src1, vecY src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 4 && VM_Version::supports_avx512dq());
+  match(Set dst (MulVL src1 src2));
+  format %{ "vpmullq $dst,$src1,$src2\t! mul packed4L" %}
+  ins_encode %{
+    int vector_len = 1;
+    __ vpmullq($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vmul4L_mem(vecY dst, vecY src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 4 && VM_Version::supports_avx512dq());
+  match(Set dst (MulVL src (LoadVector mem)));
+  format %{ "vpmullq $dst,$src,$mem\t! mul packed4L" %}
+  ins_encode %{
+    int vector_len = 1;
+    __ vpmullq($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4177,8 +6341,30 @@
   match(Set dst (MulVI src1 src2));
   format %{ "vpmulld $dst,$src1,$src2\t! mul packed8I" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpmulld($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpmulld($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vmul8L_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 8 && VM_Version::supports_avx512dq());
+  match(Set dst (MulVL src1 src2));
+  format %{ "vpmullq $dst,$src1,$src2\t! mul packed8L" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpmullq($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vmul16I_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 16);
+  match(Set dst (MulVI src1 src2));
+  format %{ "vpmulld $dst,$src1,$src2\t! mul packed16I" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpmulld($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4188,8 +6374,30 @@
   match(Set dst (MulVI src (LoadVector mem)));
   format %{ "vpmulld $dst,$src,$mem\t! mul packed8I" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpmulld($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 1;
+    __ vpmulld($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vmul8L_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 8 && VM_Version::supports_avx512dq());
+  match(Set dst (MulVL src (LoadVector mem)));
+  format %{ "vpmullq $dst,$src,$mem\t! mul packed8L" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpmullq($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vmul16I_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 16);
+  match(Set dst (MulVI src (LoadVector mem)));
+  format %{ "vpmulld $dst,$src,$mem\t! mul packed16I" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpmulld($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4210,8 +6418,8 @@
   match(Set dst (MulVF src1 src2));
   format %{ "vmulps  $dst,$src1,$src2\t! mul packed2F" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vmulps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vmulps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4231,8 +6439,8 @@
   match(Set dst (MulVF src1 src2));
   format %{ "vmulps  $dst,$src1,$src2\t! mul packed4F" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vmulps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vmulps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4242,8 +6450,8 @@
   match(Set dst (MulVF src (LoadVector mem)));
   format %{ "vmulps  $dst,$src,$mem\t! mul packed4F" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vmulps($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vmulps($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4253,8 +6461,8 @@
   match(Set dst (MulVF src1 src2));
   format %{ "vmulps  $dst,$src1,$src2\t! mul packed8F" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vmulps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vmulps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4264,8 +6472,30 @@
   match(Set dst (MulVF src (LoadVector mem)));
   format %{ "vmulps  $dst,$src,$mem\t! mul packed8F" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vmulps($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 1;
+    __ vmulps($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vmul16F_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 16);
+  match(Set dst (MulVF src1 src2));
+  format %{ "vmulps  $dst,$src1,$src2\t! mul packed16F" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vmulps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vmul16F_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 16);
+  match(Set dst (MulVF src (LoadVector mem)));
+  format %{ "vmulps  $dst,$src,$mem\t! mul packed16F" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vmulps($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4286,8 +6516,8 @@
   match(Set dst (MulVD src1 src2));
   format %{ "vmulpd  $dst,$src1,$src2\t! mul packed2D" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vmulpd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vmulpd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4297,8 +6527,8 @@
   match(Set dst (MulVD src (LoadVector mem)));
   format %{ "vmulpd  $dst,$src,$mem\t! mul packed2D" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vmulpd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vmulpd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4308,8 +6538,8 @@
   match(Set dst (MulVD src1 src2));
   format %{ "vmulpd  $dst,$src1,$src2\t! mul packed4D" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vmulpd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vmulpd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4319,8 +6549,30 @@
   match(Set dst (MulVD src (LoadVector mem)));
   format %{ "vmulpd  $dst,$src,$mem\t! mul packed4D" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vmulpd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 1;
+    __ vmulpd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vmul8D_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 8);
+  match(Set dst (MulVD src1 src2));
+  format %{ "vmulpd  $dst k0,$src1,$src2\t! mul packed8D" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vmulpd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vmul8D_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 8);
+  match(Set dst (MulVD src (LoadVector mem)));
+  format %{ "vmulpd  $dst k0,$src,$mem\t! mul packed8D" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vmulpd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4343,8 +6595,8 @@
   match(Set dst (DivVF src1 src2));
   format %{ "vdivps  $dst,$src1,$src2\t! div packed2F" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vdivps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vdivps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4364,8 +6616,8 @@
   match(Set dst (DivVF src1 src2));
   format %{ "vdivps  $dst,$src1,$src2\t! div packed4F" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vdivps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vdivps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4375,8 +6627,8 @@
   match(Set dst (DivVF src (LoadVector mem)));
   format %{ "vdivps  $dst,$src,$mem\t! div packed4F" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vdivps($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vdivps($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4386,8 +6638,8 @@
   match(Set dst (DivVF src1 src2));
   format %{ "vdivps  $dst,$src1,$src2\t! div packed8F" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vdivps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vdivps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4397,8 +6649,30 @@
   match(Set dst (DivVF src (LoadVector mem)));
   format %{ "vdivps  $dst,$src,$mem\t! div packed8F" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vdivps($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 1;
+    __ vdivps($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vdiv16F_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 0 && n->as_Vector()->length() == 16);
+  match(Set dst (DivVF src1 src2));
+  format %{ "vdivps  $dst,$src1,$src2\t! div packed16F" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vdivps($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vdiv16F_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 0 && n->as_Vector()->length() == 16);
+  match(Set dst (DivVF src (LoadVector mem)));
+  format %{ "vdivps  $dst,$src,$mem\t! div packed16F" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vdivps($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4419,8 +6693,8 @@
   match(Set dst (DivVD src1 src2));
   format %{ "vdivpd  $dst,$src1,$src2\t! div packed2D" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vdivpd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vdivpd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4430,8 +6704,8 @@
   match(Set dst (DivVD src (LoadVector mem)));
   format %{ "vdivpd  $dst,$src,$mem\t! div packed2D" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vdivpd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vdivpd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4441,8 +6715,8 @@
   match(Set dst (DivVD src1 src2));
   format %{ "vdivpd  $dst,$src1,$src2\t! div packed4D" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vdivpd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vdivpd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4452,8 +6726,30 @@
   match(Set dst (DivVD src (LoadVector mem)));
   format %{ "vdivpd  $dst,$src,$mem\t! div packed4D" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vdivpd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 1;
+    __ vdivpd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vdiv8D_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 8);
+  match(Set dst (DivVD src1 src2));
+  format %{ "vdivpd  $dst,$src1,$src2\t! div packed8D" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vdivpd($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vdiv8D_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 8);
+  match(Set dst (DivVD src (LoadVector mem)));
+  format %{ "vdivpd  $dst,$src,$mem\t! div packed8D" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vdivpd($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4500,8 +6796,8 @@
   match(Set dst (LShiftVS src shift));
   format %{ "vpsllw  $dst,$src,$shift\t! left shift packed2S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsllw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsllw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4511,8 +6807,8 @@
   match(Set dst (LShiftVS src shift));
   format %{ "vpsllw  $dst,$src,$shift\t! left shift packed2S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsllw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 0;
+    __ vpsllw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4542,8 +6838,8 @@
   match(Set dst (LShiftVS src shift));
   format %{ "vpsllw  $dst,$src,$shift\t! left shift packed4S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsllw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsllw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4553,8 +6849,8 @@
   match(Set dst (LShiftVS src shift));
   format %{ "vpsllw  $dst,$src,$shift\t! left shift packed4S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsllw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 0;
+    __ vpsllw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4584,8 +6880,8 @@
   match(Set dst (LShiftVS src shift));
   format %{ "vpsllw  $dst,$src,$shift\t! left shift packed8S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsllw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsllw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4595,8 +6891,8 @@
   match(Set dst (LShiftVS src shift));
   format %{ "vpsllw  $dst,$src,$shift\t! left shift packed8S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsllw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 0;
+    __ vpsllw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4606,8 +6902,8 @@
   match(Set dst (LShiftVS src shift));
   format %{ "vpsllw  $dst,$src,$shift\t! left shift packed16S" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsllw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpsllw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4617,8 +6913,30 @@
   match(Set dst (LShiftVS src shift));
   format %{ "vpsllw  $dst,$src,$shift\t! left shift packed16S" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsllw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 1;
+    __ vpsllw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsll32S_reg(vecZ dst, vecZ src, vecS shift) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 32);
+  match(Set dst (LShiftVS src shift));
+  format %{ "vpsllw  $dst,$src,$shift\t! left shift packed32S" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsllw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsll32S_reg_imm(vecZ dst, vecZ src, immI8 shift) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 32);
+  match(Set dst (LShiftVS src shift));
+  format %{ "vpsllw  $dst,$src,$shift\t! left shift packed32S" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsllw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4649,8 +6967,8 @@
   match(Set dst (LShiftVI src shift));
   format %{ "vpslld  $dst,$src,$shift\t! left shift packed2I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpslld($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpslld($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4660,8 +6978,8 @@
   match(Set dst (LShiftVI src shift));
   format %{ "vpslld  $dst,$src,$shift\t! left shift packed2I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpslld($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 0;
+    __ vpslld($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4691,8 +7009,8 @@
   match(Set dst (LShiftVI src shift));
   format %{ "vpslld  $dst,$src,$shift\t! left shift packed4I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpslld($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpslld($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4702,8 +7020,8 @@
   match(Set dst (LShiftVI src shift));
   format %{ "vpslld  $dst,$src,$shift\t! left shift packed4I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpslld($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 0;
+    __ vpslld($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4713,8 +7031,8 @@
   match(Set dst (LShiftVI src shift));
   format %{ "vpslld  $dst,$src,$shift\t! left shift packed8I" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpslld($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpslld($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4724,8 +7042,30 @@
   match(Set dst (LShiftVI src shift));
   format %{ "vpslld  $dst,$src,$shift\t! left shift packed8I" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpslld($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 1;
+    __ vpslld($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsll16I_reg(vecZ dst, vecZ src, vecS shift) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 16);
+  match(Set dst (LShiftVI src shift));
+  format %{ "vpslld  $dst,$src,$shift\t! left shift packed16I" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpslld($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsll16I_reg_imm(vecZ dst, vecZ src, immI8 shift) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 16);
+  match(Set dst (LShiftVI src shift));
+  format %{ "vpslld  $dst,$src,$shift\t! left shift packed16I" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpslld($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4756,8 +7096,8 @@
   match(Set dst (LShiftVL src shift));
   format %{ "vpsllq  $dst,$src,$shift\t! left shift packed2L" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsllq($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsllq($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4767,8 +7107,8 @@
   match(Set dst (LShiftVL src shift));
   format %{ "vpsllq  $dst,$src,$shift\t! left shift packed2L" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsllq($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 0;
+    __ vpsllq($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4778,8 +7118,8 @@
   match(Set dst (LShiftVL src shift));
   format %{ "vpsllq  $dst,$src,$shift\t! left shift packed4L" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsllq($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpsllq($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4789,8 +7129,30 @@
   match(Set dst (LShiftVL src shift));
   format %{ "vpsllq  $dst,$src,$shift\t! left shift packed4L" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsllq($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 1;
+    __ vpsllq($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsll8L_reg(vecZ dst, vecZ src, vecS shift) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 8);
+  match(Set dst (LShiftVL src shift));
+  format %{ "vpsllq  $dst,$src,$shift\t! left shift packed8L" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsllq($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsll8L_reg_imm(vecZ dst, vecZ src, immI8 shift) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 8);
+  match(Set dst (LShiftVL src shift));
+  format %{ "vpsllq  $dst,$src,$shift\t! left shift packed8L" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsllq($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4827,8 +7189,8 @@
   match(Set dst (URShiftVS src shift));
   format %{ "vpsrlw  $dst,$src,$shift\t! logical right shift packed2S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsrlw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsrlw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4838,8 +7200,8 @@
   match(Set dst (URShiftVS src shift));
   format %{ "vpsrlw  $dst,$src,$shift\t! logical right shift packed2S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsrlw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 0;
+    __ vpsrlw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4869,8 +7231,8 @@
   match(Set dst (URShiftVS src shift));
   format %{ "vpsrlw  $dst,$src,$shift\t! logical right shift packed4S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsrlw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsrlw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4880,8 +7242,8 @@
   match(Set dst (URShiftVS src shift));
   format %{ "vpsrlw  $dst,$src,$shift\t! logical right shift packed4S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsrlw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 0;
+    __ vpsrlw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4911,8 +7273,8 @@
   match(Set dst (URShiftVS src shift));
   format %{ "vpsrlw  $dst,$src,$shift\t! logical right shift packed8S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsrlw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsrlw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4922,8 +7284,8 @@
   match(Set dst (URShiftVS src shift));
   format %{ "vpsrlw  $dst,$src,$shift\t! logical right shift packed8S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsrlw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 0;
+    __ vpsrlw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4933,8 +7295,8 @@
   match(Set dst (URShiftVS src shift));
   format %{ "vpsrlw  $dst,$src,$shift\t! logical right shift packed16S" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsrlw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpsrlw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4944,8 +7306,30 @@
   match(Set dst (URShiftVS src shift));
   format %{ "vpsrlw  $dst,$src,$shift\t! logical right shift packed16S" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsrlw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 1;
+    __ vpsrlw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsrl32S_reg(vecZ dst, vecZ src, vecS shift) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 32);
+  match(Set dst (URShiftVS src shift));
+  format %{ "vpsrlw  $dst,$src,$shift\t! logical right shift packed32S" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsrlw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsrl32S_reg_imm(vecZ dst, vecZ src, immI8 shift) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 32);
+  match(Set dst (URShiftVS src shift));
+  format %{ "vpsrlw  $dst,$src,$shift\t! logical right shift packed32S" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsrlw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4976,8 +7360,8 @@
   match(Set dst (URShiftVI src shift));
   format %{ "vpsrld  $dst,$src,$shift\t! logical right shift packed2I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsrld($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsrld($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -4987,8 +7371,8 @@
   match(Set dst (URShiftVI src shift));
   format %{ "vpsrld  $dst,$src,$shift\t! logical right shift packed2I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsrld($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 0;
+    __ vpsrld($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5018,8 +7402,8 @@
   match(Set dst (URShiftVI src shift));
   format %{ "vpsrld  $dst,$src,$shift\t! logical right shift packed4I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsrld($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsrld($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5029,8 +7413,8 @@
   match(Set dst (URShiftVI src shift));
   format %{ "vpsrld  $dst,$src,$shift\t! logical right shift packed4I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsrld($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 0;
+    __ vpsrld($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5040,8 +7424,8 @@
   match(Set dst (URShiftVI src shift));
   format %{ "vpsrld  $dst,$src,$shift\t! logical right shift packed8I" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsrld($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpsrld($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5051,8 +7435,30 @@
   match(Set dst (URShiftVI src shift));
   format %{ "vpsrld  $dst,$src,$shift\t! logical right shift packed8I" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsrld($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 1;
+    __ vpsrld($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsrl16I_reg(vecZ dst, vecZ src, vecS shift) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 16);
+  match(Set dst (URShiftVI src shift));
+  format %{ "vpsrld  $dst,$src,$shift\t! logical right shift packed16I" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsrld($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsrl16I_reg_imm(vecZ dst, vecZ src, immI8 shift) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 16);
+  match(Set dst (URShiftVI src shift));
+  format %{ "vpsrld  $dst,$src,$shift\t! logical right shift packed16I" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsrld($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5083,8 +7489,8 @@
   match(Set dst (URShiftVL src shift));
   format %{ "vpsrlq  $dst,$src,$shift\t! logical right shift packed2L" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsrlq($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsrlq($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5094,8 +7500,8 @@
   match(Set dst (URShiftVL src shift));
   format %{ "vpsrlq  $dst,$src,$shift\t! logical right shift packed2L" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsrlq($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 0;
+    __ vpsrlq($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5105,8 +7511,8 @@
   match(Set dst (URShiftVL src shift));
   format %{ "vpsrlq  $dst,$src,$shift\t! logical right shift packed4L" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsrlq($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpsrlq($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5116,8 +7522,30 @@
   match(Set dst (URShiftVL src shift));
   format %{ "vpsrlq  $dst,$src,$shift\t! logical right shift packed4L" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsrlq($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 1;
+    __ vpsrlq($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsrl8L_reg(vecZ dst, vecZ src, vecS shift) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 8);
+  match(Set dst (URShiftVL src shift));
+  format %{ "vpsrlq  $dst,$src,$shift\t! logical right shift packed8L" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsrlq($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsrl8L_reg_imm(vecZ dst, vecZ src, immI8 shift) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 8);
+  match(Set dst (URShiftVL src shift));
+  format %{ "vpsrlq  $dst,$src,$shift\t! logical right shift packed8L" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsrlq($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5150,8 +7578,8 @@
   match(Set dst (RShiftVS src shift));
   format %{ "vpsraw  $dst,$src,$shift\t! arithmetic right shift packed2S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsraw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsraw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5161,8 +7589,8 @@
   match(Set dst (RShiftVS src shift));
   format %{ "vpsraw  $dst,$src,$shift\t! arithmetic right shift packed2S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsraw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 0;
+    __ vpsraw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5192,8 +7620,8 @@
   match(Set dst (RShiftVS src shift));
   format %{ "vpsraw  $dst,$src,$shift\t! arithmetic right shift packed4S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsraw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsraw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5203,8 +7631,8 @@
   match(Set dst (RShiftVS src shift));
   format %{ "vpsraw  $dst,$src,$shift\t! arithmetic right shift packed4S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsraw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 0;
+    __ vpsraw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5234,8 +7662,8 @@
   match(Set dst (RShiftVS src shift));
   format %{ "vpsraw  $dst,$src,$shift\t! arithmetic right shift packed8S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsraw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsraw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5245,8 +7673,8 @@
   match(Set dst (RShiftVS src shift));
   format %{ "vpsraw  $dst,$src,$shift\t! arithmetic right shift packed8S" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsraw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 0;
+    __ vpsraw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5256,8 +7684,8 @@
   match(Set dst (RShiftVS src shift));
   format %{ "vpsraw  $dst,$src,$shift\t! arithmetic right shift packed16S" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsraw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpsraw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5267,8 +7695,30 @@
   match(Set dst (RShiftVS src shift));
   format %{ "vpsraw  $dst,$src,$shift\t! arithmetic right shift packed16S" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsraw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 1;
+    __ vpsraw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsra32S_reg(vecZ dst, vecZ src, vecS shift) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 32);
+  match(Set dst (RShiftVS src shift));
+  format %{ "vpsraw  $dst,$src,$shift\t! arithmetic right shift packed32S" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsraw($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsra32S_reg_imm(vecZ dst, vecZ src, immI8 shift) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 32);
+  match(Set dst (RShiftVS src shift));
+  format %{ "vpsraw  $dst,$src,$shift\t! arithmetic right shift packed32S" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsraw($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5299,8 +7749,8 @@
   match(Set dst (RShiftVI src shift));
   format %{ "vpsrad  $dst,$src,$shift\t! arithmetic right shift packed2I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsrad($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsrad($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5310,8 +7760,8 @@
   match(Set dst (RShiftVI src shift));
   format %{ "vpsrad  $dst,$src,$shift\t! arithmetic right shift packed2I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsrad($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 0;
+    __ vpsrad($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5341,8 +7791,8 @@
   match(Set dst (RShiftVI src shift));
   format %{ "vpsrad  $dst,$src,$shift\t! arithmetic right shift packed4I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsrad($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpsrad($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5352,8 +7802,8 @@
   match(Set dst (RShiftVI src shift));
   format %{ "vpsrad  $dst,$src,$shift\t! arithmetic right shift packed4I" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpsrad($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 0;
+    __ vpsrad($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5363,8 +7813,8 @@
   match(Set dst (RShiftVI src shift));
   format %{ "vpsrad  $dst,$src,$shift\t! arithmetic right shift packed8I" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsrad($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpsrad($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5374,8 +7824,30 @@
   match(Set dst (RShiftVI src shift));
   format %{ "vpsrad  $dst,$src,$shift\t! arithmetic right shift packed8I" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpsrad($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector256);
+    int vector_len = 1;
+    __ vpsrad($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsra16I_reg(vecZ dst, vecZ src, vecS shift) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 16);
+  match(Set dst (RShiftVI src shift));
+  format %{ "vpsrad  $dst,$src,$shift\t! arithmetic right shift packed16I" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsrad($dst$$XMMRegister, $src$$XMMRegister, $shift$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vsra16I_reg_imm(vecZ dst, vecZ src, immI8 shift) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length() == 16);
+  match(Set dst (RShiftVI src shift));
+  format %{ "vpsrad  $dst,$src,$shift\t! arithmetic right shift packed16I" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpsrad($dst$$XMMRegister, $src$$XMMRegister, (int)$shift$$constant, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5400,8 +7872,8 @@
   match(Set dst (AndV src1 src2));
   format %{ "vpand   $dst,$src1,$src2\t! and vectors (4 bytes)" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpand($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpand($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5421,8 +7893,8 @@
   match(Set dst (AndV src1 src2));
   format %{ "vpand   $dst,$src1,$src2\t! and vectors (8 bytes)" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpand($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpand($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5442,8 +7914,8 @@
   match(Set dst (AndV src1 src2));
   format %{ "vpand   $dst,$src1,$src2\t! and vectors (16 bytes)" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpand($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpand($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5453,8 +7925,8 @@
   match(Set dst (AndV src (LoadVector mem)));
   format %{ "vpand   $dst,$src,$mem\t! and vectors (16 bytes)" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpand($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vpand($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5464,8 +7936,8 @@
   match(Set dst (AndV src1 src2));
   format %{ "vpand   $dst,$src1,$src2\t! and vectors (32 bytes)" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpand($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpand($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5475,8 +7947,30 @@
   match(Set dst (AndV src (LoadVector mem)));
   format %{ "vpand   $dst,$src,$mem\t! and vectors (32 bytes)" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpand($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 1;
+    __ vpand($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vand64B_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length_in_bytes() == 64);
+  match(Set dst (AndV src1 src2));
+  format %{ "vpand   $dst,$src1,$src2\t! and vectors (64 bytes)" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpand($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vand64B_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length_in_bytes() == 64);
+  match(Set dst (AndV src (LoadVector mem)));
+  format %{ "vpand   $dst,$src,$mem\t! and vectors (64 bytes)" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpand($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5498,8 +7992,8 @@
   match(Set dst (OrV src1 src2));
   format %{ "vpor    $dst,$src1,$src2\t! or vectors (4 bytes)" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpor($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpor($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5519,8 +8013,8 @@
   match(Set dst (OrV src1 src2));
   format %{ "vpor    $dst,$src1,$src2\t! or vectors (8 bytes)" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpor($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpor($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5540,8 +8034,8 @@
   match(Set dst (OrV src1 src2));
   format %{ "vpor    $dst,$src1,$src2\t! or vectors (16 bytes)" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpor($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpor($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5551,8 +8045,8 @@
   match(Set dst (OrV src (LoadVector mem)));
   format %{ "vpor    $dst,$src,$mem\t! or vectors (16 bytes)" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpor($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vpor($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5562,8 +8056,8 @@
   match(Set dst (OrV src1 src2));
   format %{ "vpor    $dst,$src1,$src2\t! or vectors (32 bytes)" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpor($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpor($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5573,8 +8067,30 @@
   match(Set dst (OrV src (LoadVector mem)));
   format %{ "vpor    $dst,$src,$mem\t! or vectors (32 bytes)" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpor($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 1;
+    __ vpor($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vor64B_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length_in_bytes() == 64);
+  match(Set dst (OrV src1 src2));
+  format %{ "vpor    $dst,$src1,$src2\t! or vectors (64 bytes)" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpor($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vor64B_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length_in_bytes() == 64);
+  match(Set dst (OrV src (LoadVector mem)));
+  format %{ "vpor    $dst,$src,$mem\t! or vectors (64 bytes)" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpor($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5596,8 +8112,8 @@
   match(Set dst (XorV src1 src2));
   format %{ "vpxor   $dst,$src1,$src2\t! xor vectors (4 bytes)" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpxor($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpxor($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5617,8 +8133,8 @@
   match(Set dst (XorV src1 src2));
   format %{ "vpxor   $dst,$src1,$src2\t! xor vectors (8 bytes)" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpxor($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpxor($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5638,8 +8154,8 @@
   match(Set dst (XorV src1 src2));
   format %{ "vpxor   $dst,$src1,$src2\t! xor vectors (16 bytes)" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpxor($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 0;
+    __ vpxor($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5649,8 +8165,8 @@
   match(Set dst (XorV src (LoadVector mem)));
   format %{ "vpxor   $dst,$src,$mem\t! xor vectors (16 bytes)" %}
   ins_encode %{
-    bool vector256 = false;
-    __ vpxor($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
+    int vector_len = 0;
+    __ vpxor($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5660,8 +8176,8 @@
   match(Set dst (XorV src1 src2));
   format %{ "vpxor   $dst,$src1,$src2\t! xor vectors (32 bytes)" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpxor($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector256);
+    int vector_len = 1;
+    __ vpxor($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
   %}
   ins_pipe( pipe_slow );
 %}
@@ -5671,9 +8187,31 @@
   match(Set dst (XorV src (LoadVector mem)));
   format %{ "vpxor   $dst,$src,$mem\t! xor vectors (32 bytes)" %}
   ins_encode %{
-    bool vector256 = true;
-    __ vpxor($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector256);
-  %}
-  ins_pipe( pipe_slow );
-%}
-
+    int vector_len = 1;
+    __ vpxor($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vxor64B_reg(vecZ dst, vecZ src1, vecZ src2) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length_in_bytes() == 64);
+  match(Set dst (XorV src1 src2));
+  format %{ "vpxor   $dst,$src1,$src2\t! xor vectors (64 bytes)" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpxor($dst$$XMMRegister, $src1$$XMMRegister, $src2$$XMMRegister, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
+instruct vxor64B_mem(vecZ dst, vecZ src, memory mem) %{
+  predicate(UseAVX > 2 && n->as_Vector()->length_in_bytes() == 64);
+  match(Set dst (XorV src (LoadVector mem)));
+  format %{ "vpxor   $dst,$src,$mem\t! xor vectors (64 bytes)" %}
+  ins_encode %{
+    int vector_len = 2;
+    __ vpxor($dst$$XMMRegister, $src$$XMMRegister, $mem$$Address, vector_len);
+  %}
+  ins_pipe( pipe_slow );
+%}
+
--- a/hotspot/src/cpu/x86/vm/x86_32.ad	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/x86_32.ad	Wed Jul 05 20:35:10 2017 +0200
@@ -101,6 +101,17 @@
 reg_def FPR6H( SOC, SOC, Op_RegF, 6, as_FloatRegister(5)->as_VMReg()->next());
 reg_def FPR7L( SOC, SOC, Op_RegF, 7, as_FloatRegister(6)->as_VMReg());
 reg_def FPR7H( SOC, SOC, Op_RegF, 7, as_FloatRegister(6)->as_VMReg()->next());
+//
+// Empty fill registers, which are never used, but supply alignment to xmm regs
+//
+reg_def FILL0( SOC, SOC, Op_RegF, 7, as_FloatRegister(6)->as_VMReg()->next(2));
+reg_def FILL1( SOC, SOC, Op_RegF, 7, as_FloatRegister(6)->as_VMReg()->next(3));
+reg_def FILL2( SOC, SOC, Op_RegF, 7, as_FloatRegister(6)->as_VMReg()->next(4));
+reg_def FILL3( SOC, SOC, Op_RegF, 7, as_FloatRegister(6)->as_VMReg()->next(5));
+reg_def FILL4( SOC, SOC, Op_RegF, 7, as_FloatRegister(6)->as_VMReg()->next(6));
+reg_def FILL5( SOC, SOC, Op_RegF, 7, as_FloatRegister(6)->as_VMReg()->next(7));
+reg_def FILL6( SOC, SOC, Op_RegF, 7, as_FloatRegister(6)->as_VMReg()->next(8));
+reg_def FILL7( SOC, SOC, Op_RegF, 7, as_FloatRegister(6)->as_VMReg()->next(9));
 
 // Specify priority of register selection within phases of register
 // allocation.  Highest priority is first.  A useful heuristic is to
@@ -112,7 +123,8 @@
 alloc_class chunk0( ECX,   EBX,   EBP,   EDI,   EAX,   EDX,   ESI, ESP,
                     FPR0L, FPR0H, FPR1L, FPR1H, FPR2L, FPR2H,
                     FPR3L, FPR3H, FPR4L, FPR4H, FPR5L, FPR5H,
-                    FPR6L, FPR6H, FPR7L, FPR7H );
+                    FPR6L, FPR6H, FPR7L, FPR7H,
+                    FILL0, FILL1, FILL2, FILL3, FILL4, FILL5, FILL6, FILL7);
 
 
 //----------Architecture Description Register Classes--------------------------
@@ -131,7 +143,7 @@
 // Class for all registers (excluding EBP)
 reg_class any_reg_no_ebp(EAX, EDX, EDI, ESI, ECX, EBX, ESP);
 // Dynamic register class that selects at runtime between register classes
-// any_reg and any_no_ebp_reg (depending on the value of the flag PreserveFramePointer). 
+// any_reg and any_no_ebp_reg (depending on the value of the flag PreserveFramePointer).
 // Equivalent to: return PreserveFramePointer ? any_no_ebp_reg : any_reg;
 reg_class_dynamic any_reg(any_reg_no_ebp, any_reg_with_ebp, %{ PreserveFramePointer %});
 
@@ -279,7 +291,9 @@
     size += 6; // fldcw
   }
   if (C->max_vector_size() > 16) {
-    size += 3; // vzeroupper
+    if(UseAVX <= 2) {
+      size += 3; // vzeroupper
+    }
   }
   return size;
 }
@@ -288,7 +302,7 @@
 //       from the start of the call to the point where the return address
 //       will point.
 int MachCallStaticJavaNode::ret_addr_offset() {
-  return 5 + pre_call_resets_size();  // 5 bytes from start of call to where return address points  
+  return 5 + pre_call_resets_size();  // 5 bytes from start of call to where return address points
 }
 
 int MachCallDynamicJavaNode::ret_addr_offset() {
@@ -767,6 +781,12 @@
 // Helper for XMM registers.  Extra opcode bits, limited syntax.
 static int impl_x_helper( CodeBuffer *cbuf, bool do_size, bool is_load,
                          int offset, int reg_lo, int reg_hi, int size, outputStream* st ) {
+  int in_size_in_bits = Assembler::EVEX_32bit;
+  int evex_encoding = 0;
+  if (reg_lo+1 == reg_hi) {
+    in_size_in_bits = Assembler::EVEX_64bit;
+    evex_encoding = Assembler::VEX_W;
+  }
   if (cbuf) {
     MacroAssembler _masm(cbuf);
     if (reg_lo+1 == reg_hi) { // double move?
@@ -799,7 +819,17 @@
     }
 #endif
   }
-  int offset_size = (offset == 0) ? 0 : ((offset <= 127) ? 1 : 4);
+  bool is_single_byte = false;
+  if ((UseAVX > 2) && (offset != 0)) {
+    is_single_byte = Assembler::query_compressed_disp_byte(offset, true, 0, Assembler::EVEX_T1S, in_size_in_bits, evex_encoding);
+  }
+  int offset_size = 0;
+  if (UseAVX > 2 ) {
+    offset_size = (offset == 0) ? 0 : ((is_single_byte) ? 1 : 4);
+  } else {
+    offset_size = (offset == 0) ? 0 : ((offset <= 127) ? 1 : 4);
+  }
+  size += (UseAVX > 2) ? 2 : 0; // Need an additional two bytes for EVEX
   // VEX_2bytes prefix is used if UseAVX > 0, so it takes the same 2 bytes as SIMD prefix.
   return size+5+offset_size;
 }
@@ -835,8 +865,8 @@
 #endif
   }
   // VEX_2bytes prefix is used if UseAVX > 0, and it takes the same 2 bytes as SIMD prefix.
-  // Only MOVAPS SSE prefix uses 1 byte.
-  int sz = 4;
+  // Only MOVAPS SSE prefix uses 1 byte.  EVEX uses an additional 2 bytes.
+  int sz = (UseAVX > 2) ? 6 : 4;
   if (!(src_lo+1 == src_hi && dst_lo+1 == dst_hi) &&
       UseXmmRegToRegMoveAll && (UseAVX == 0)) sz = 3;
   return size + sz;
@@ -854,7 +884,7 @@
     st->print("movdl   %s, %s\t# spill", Matcher::regName[dst_lo], Matcher::regName[src_lo]);
 #endif
   }
-  return 4;
+  return (UseAVX> 2) ? 6 : 4;
 }
 
 
@@ -870,7 +900,7 @@
     st->print("movdl   %s, %s\t# spill", Matcher::regName[dst_lo], Matcher::regName[src_lo]);
 #endif
   }
-  return 4;
+  return (UseAVX> 2) ? 6 : 4;
 }
 
 static int impl_mov_helper( CodeBuffer *cbuf, bool do_size, int src, int dst, int size, outputStream* st ) {
@@ -941,9 +971,8 @@
     calc_size += 3+src_offset_size + 3+dst_offset_size;
     break;
   case Op_VecX:
-    calc_size = 6 + 6 + 5+src_offset_size + 5+dst_offset_size;
-    break;
   case Op_VecY:
+  case Op_VecZ:
     calc_size = 6 + 6 + 5+src_offset_size + 5+dst_offset_size;
     break;
   default:
@@ -974,6 +1003,11 @@
       __ vmovdqu(xmm0, Address(rsp, src_offset));
       __ vmovdqu(Address(rsp, dst_offset), xmm0);
       __ vmovdqu(xmm0, Address(rsp, -32));
+    case Op_VecZ:
+      __ evmovdqu(Address(rsp, -64), xmm0, 2);
+      __ evmovdqu(xmm0, Address(rsp, src_offset), 2);
+      __ evmovdqu(Address(rsp, dst_offset), xmm0, 2);
+      __ evmovdqu(xmm0, Address(rsp, -64), 2);
       break;
     default:
       ShouldNotReachHere();
@@ -1009,6 +1043,12 @@
                 "vmovdqu [rsp + #%d], xmm0\n\t"
                 "vmovdqu xmm0, [rsp - #32]",
                 src_offset, dst_offset);
+    case Op_VecZ:
+      st->print("vmovdqu [rsp - #64], xmm0\t# 512-bit mem-mem spill\n\t"
+                "vmovdqu xmm0, [rsp + #%d]\n\t"
+                "vmovdqu [rsp + #%d], xmm0\n\t"
+                "vmovdqu xmm0, [rsp - #64]",
+                src_offset, dst_offset);
       break;
     default:
       ShouldNotReachHere();
@@ -1042,7 +1082,7 @@
     uint ireg = ideal_reg();
     assert((src_first_rc != rc_int && dst_first_rc != rc_int), "sanity");
     assert((src_first_rc != rc_float && dst_first_rc != rc_float), "sanity");
-    assert((ireg == Op_VecS || ireg == Op_VecD || ireg == Op_VecX || ireg == Op_VecY), "sanity");
+    assert((ireg == Op_VecS || ireg == Op_VecD || ireg == Op_VecX || ireg == Op_VecY || ireg == Op_VecZ ), "sanity");
     if( src_first_rc == rc_stack && dst_first_rc == rc_stack ) {
       // mem -> mem
       int src_offset = ra_->reg2offset(src_first);
@@ -3998,7 +4038,7 @@
 // XMM Float register operands
 operand regF() %{
   predicate( UseSSE>=1 );
-  constraint(ALLOC_IN_RC(float_reg));
+  constraint(ALLOC_IN_RC(float_reg_legacy));
   match(RegF);
   format %{ %}
   interface(REG_INTER);
@@ -4007,12 +4047,45 @@
 // XMM Double register operands
 operand regD() %{
   predicate( UseSSE>=2 );
-  constraint(ALLOC_IN_RC(double_reg));
+  constraint(ALLOC_IN_RC(double_reg_legacy));
   match(RegD);
   format %{ %}
   interface(REG_INTER);
 %}
 
+// Vectors : note, we use legacy registers to avoid extra (unneeded in 32-bit VM)
+// runtime code generation via reg_class_dynamic.
+operand vecS() %{
+  constraint(ALLOC_IN_RC(vectors_reg_legacy));
+  match(VecS);
+
+  format %{ %}
+  interface(REG_INTER);
+%}
+
+operand vecD() %{
+  constraint(ALLOC_IN_RC(vectord_reg_legacy));
+  match(VecD);
+
+  format %{ %}
+  interface(REG_INTER);
+%}
+
+operand vecX() %{
+  constraint(ALLOC_IN_RC(vectorx_reg_legacy));
+  match(VecX);
+
+  format %{ %}
+  interface(REG_INTER);
+%}
+
+operand vecY() %{
+  constraint(ALLOC_IN_RC(vectory_reg_legacy));
+  match(VecY);
+
+  format %{ %}
+  interface(REG_INTER);
+%}
 
 //----------Memory Operands----------------------------------------------------
 // Direct Memory Operand
@@ -5020,11 +5093,11 @@
   match(Set dst (ReverseBytesUS dst));
   effect(KILL cr);
 
-  format %{ "BSWAP  $dst\n\t" 
+  format %{ "BSWAP  $dst\n\t"
             "SHR    $dst,16\n\t" %}
   ins_encode %{
     __ bswapl($dst$$Register);
-    __ shrl($dst$$Register, 16); 
+    __ shrl($dst$$Register, 16);
   %}
   ins_pipe( ialu_reg );
 %}
@@ -5033,11 +5106,11 @@
   match(Set dst (ReverseBytesS dst));
   effect(KILL cr);
 
-  format %{ "BSWAP  $dst\n\t" 
+  format %{ "BSWAP  $dst\n\t"
             "SAR    $dst,16\n\t" %}
   ins_encode %{
     __ bswapl($dst$$Register);
-    __ sarl($dst$$Register, 16); 
+    __ sarl($dst$$Register, 16);
   %}
   ins_pipe( ialu_reg );
 %}
@@ -6525,7 +6598,7 @@
   effect(KILL cr);
   ins_cost(400);
 
-  format %{ 
+  format %{
     $$template
     if (os::is_MP()) {
       $$emit$$"LOCK ADDL [ESP + #0], 0\t! membar_volatile"
@@ -8288,10 +8361,10 @@
 
 // Xor Register with Immediate -1
 instruct xorI_eReg_im1(rRegI dst, immI_M1 imm) %{
-  match(Set dst (XorI dst imm));  
+  match(Set dst (XorI dst imm));
 
   size(2);
-  format %{ "NOT    $dst" %}  
+  format %{ "NOT    $dst" %}
   ins_encode %{
      __ notl($dst$$Register);
   %}
@@ -8939,7 +9012,7 @@
 
 // Xor Long Register with Immediate -1
 instruct xorl_eReg_im1(eRegL dst, immL_M1 imm) %{
-  match(Set dst (XorL dst imm));  
+  match(Set dst (XorL dst imm));
   format %{ "NOT    $dst.lo\n\t"
             "NOT    $dst.hi" %}
   ins_encode %{
@@ -8994,7 +9067,7 @@
   effect(KILL cr);
   ins_cost(100);
   format %{ "ADD    $dst.lo,$dst.lo\n\t"
-            "ADC    $dst.hi,$dst.hi\n\t" 
+            "ADC    $dst.hi,$dst.hi\n\t"
             "ADD    $dst.lo,$dst.lo\n\t"
             "ADC    $dst.hi,$dst.hi" %}
   ins_encode %{
@@ -9013,9 +9086,9 @@
   effect(KILL cr);
   ins_cost(100);
   format %{ "ADD    $dst.lo,$dst.lo\n\t"
-            "ADC    $dst.hi,$dst.hi\n\t" 
+            "ADC    $dst.hi,$dst.hi\n\t"
             "ADD    $dst.lo,$dst.lo\n\t"
-            "ADC    $dst.hi,$dst.hi\n\t" 
+            "ADC    $dst.hi,$dst.hi\n\t"
             "ADD    $dst.lo,$dst.lo\n\t"
             "ADC    $dst.hi,$dst.hi" %}
   ins_encode %{
@@ -11168,7 +11241,6 @@
   ins_pipe( ialu_reg_reg );
 %}
 
-
 instruct MoveF2I_stack_reg(rRegI dst, stackSlotF src) %{
   match(Set dst (MoveF2I src));
   effect( DEF dst, USE src );
@@ -11400,7 +11472,7 @@
   format %{ "XOR    EAX,EAX\t# ClearArray:\n\t"
             "SHL    ECX,1\t# Convert doublewords to words\n\t"
             "REP STOS\t# store EAX into [EDI++] while ECX--" %}
-  ins_encode %{ 
+  ins_encode %{
     __ clear_mem($base$$Register, $cnt$$Register, $zero$$Register);
   %}
   ins_pipe( pipe_slow );
@@ -11413,7 +11485,7 @@
   format %{ "XOR    EAX,EAX\t# ClearArray:\n\t"
             "SHL    ECX,3\t# Convert doublewords to bytes\n\t"
             "REP STOSB\t# store EAX into [EDI++] while ECX--" %}
-  ins_encode %{ 
+  ins_encode %{
     __ clear_mem($base$$Register, $cnt$$Register, $zero$$Register);
   %}
   ins_pipe( pipe_slow );
--- a/hotspot/src/cpu/x86/vm/x86_64.ad	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/x86/vm/x86_64.ad	Wed Jul 05 20:35:10 2017 +0200
@@ -172,7 +172,7 @@
 // Class for all pointer registers (including RSP and RBP)
 reg_class any_reg_with_rbp(RAX, RAX_H,
                            RDX, RDX_H,
-                           RBP, RBP_H,               
+                           RBP, RBP_H,
                            RDI, RDI_H,
                            RSI, RSI_H,
                            RCX, RCX_H,
@@ -189,7 +189,7 @@
 
 // Class for all pointer registers (including RSP, but excluding RBP)
 reg_class any_reg_no_rbp(RAX, RAX_H,
-                         RDX, RDX_H,                
+                         RDX, RDX_H,
                          RDI, RDI_H,
                          RSI, RSI_H,
                          RCX, RCX_H,
@@ -205,10 +205,10 @@
                          R15, R15_H);
 
 // Dynamic register class that selects at runtime between register classes
-// any_reg_no_rbp and any_reg_with_rbp (depending on the value of the flag PreserveFramePointer). 
+// any_reg_no_rbp and any_reg_with_rbp (depending on the value of the flag PreserveFramePointer).
 // Equivalent to: return PreserveFramePointer ? any_reg_no_rbp : any_reg_with_rbp;
 reg_class_dynamic any_reg(any_reg_no_rbp, any_reg_with_rbp, %{ PreserveFramePointer %});
-                  
+
 // Class for all pointer registers (excluding RSP)
 reg_class ptr_reg_with_rbp(RAX, RAX_H,
                            RDX, RDX_H,
@@ -226,7 +226,7 @@
 
 // Class for all pointer registers (excluding RSP and RBP)
 reg_class ptr_reg_no_rbp(RAX, RAX_H,
-                         RDX, RDX_H,                         
+                         RDX, RDX_H,
                          RDI, RDI_H,
                          RSI, RSI_H,
                          RCX, RCX_H,
@@ -536,7 +536,11 @@
 #define __ _masm.
 
 static int clear_avx_size() {
-  return (Compile::current()->max_vector_size() > 16) ? 3 : 0;  // vzeroupper
+  if(UseAVX > 2) {
+    return 0; // vzeroupper is ignored
+  } else {
+    return (Compile::current()->max_vector_size() > 16) ? 3 : 0;  // vzeroupper
+  }
 }
 
 // !!!!! Special hack to get all types of calls to specify the byte offset
@@ -545,7 +549,7 @@
 int MachCallStaticJavaNode::ret_addr_offset()
 {
   int offset = 5; // 5 bytes from start of call to where return address points
-  offset += clear_avx_size();  
+  offset += clear_avx_size();
   return offset;
 }
 
@@ -860,7 +864,7 @@
     st->print("subq    rsp, #%d\t# Create frame",framesize);
     st->print("\n\t");
     framesize -= wordSize;
-    st->print("movq    [rsp + #%d], rbp\t# Save rbp",framesize);    
+    st->print("movq    [rsp + #%d], rbp\t# Save rbp",framesize);
     if (PreserveFramePointer) {
       st->print("\n\t");
       st->print("movq    rbp, [rsp + #%d]\t# Save the caller's SP into rbp", (framesize + wordSize));
@@ -1070,6 +1074,11 @@
       __ vmovdqu(xmm0, Address(rsp, src_offset));
       __ vmovdqu(Address(rsp, dst_offset), xmm0);
       __ vmovdqu(xmm0, Address(rsp, -32));
+    case Op_VecZ:
+      __ evmovdqu(Address(rsp, -64), xmm0, 2);
+      __ evmovdqu(xmm0, Address(rsp, src_offset), 2);
+      __ evmovdqu(Address(rsp, dst_offset), xmm0, 2);
+      __ evmovdqu(xmm0, Address(rsp, -64), 2);
       break;
     default:
       ShouldNotReachHere();
@@ -1103,6 +1112,13 @@
                 "vmovdqu xmm0, [rsp - #32]",
                 src_offset, dst_offset);
       break;
+    case Op_VecZ:
+      st->print("vmovdqu [rsp - #64], xmm0\t# 512-bit mem-mem spill\n\t"
+                "vmovdqu xmm0, [rsp + #%d]\n\t"
+                "vmovdqu [rsp + #%d], xmm0\n\t"
+                "vmovdqu xmm0, [rsp - #64]",
+                src_offset, dst_offset);
+      break;
     default:
       ShouldNotReachHere();
     }
@@ -1136,7 +1152,7 @@
   if (bottom_type()->isa_vect() != NULL) {
     uint ireg = ideal_reg();
     assert((src_first_rc != rc_int && dst_first_rc != rc_int), "sanity");
-    assert((ireg == Op_VecS || ireg == Op_VecD || ireg == Op_VecX || ireg == Op_VecY), "sanity");
+    assert((ireg == Op_VecS || ireg == Op_VecD || ireg == Op_VecX || ireg == Op_VecY || ireg == Op_VecZ ), "sanity");
     if( src_first_rc == rc_stack && dst_first_rc == rc_stack ) {
       // mem -> mem
       int src_offset = ra_->reg2offset(src_first);
@@ -1573,7 +1589,7 @@
   return MachNode::size(ra_); // too many variables; just compute it
                               // the hard way
 }
- 
+
 
 //=============================================================================
 
@@ -2832,7 +2848,7 @@
       RAX_H_num     // Op_RegL
     };
     // Excluded flags and vector registers.
-    assert(ARRAY_SIZE(hi) == _last_machine_leaf - 5, "missing type");
+    assert(ARRAY_SIZE(hi) == _last_machine_leaf - 6, "missing type");
     return OptoRegPair(hi[ideal_reg], lo[ideal_reg]);
   %}
 %}
@@ -3335,7 +3351,7 @@
 // Pointer Register
 operand any_RegP()
 %{
-  constraint(ALLOC_IN_RC(any_reg));  
+  constraint(ALLOC_IN_RC(any_reg));
   match(RegP);
   match(rax_RegP);
   match(rbx_RegP);
@@ -3589,20 +3605,51 @@
 %}
 
 // Float register operands
-operand regF()
-%{
-  constraint(ALLOC_IN_RC(float_reg));
-  match(RegF);
+operand regF() %{
+   constraint(ALLOC_IN_RC(float_reg));
+   match(RegF);
+
+   format %{ %}
+   interface(REG_INTER);
+%}
+
+// Double register operands
+operand regD() %{
+   constraint(ALLOC_IN_RC(double_reg));
+   match(RegD);
+
+   format %{ %}
+   interface(REG_INTER);
+%}
+
+// Vectors
+operand vecS() %{
+  constraint(ALLOC_IN_RC(vectors_reg));
+  match(VecS);
 
   format %{ %}
   interface(REG_INTER);
 %}
 
-// Double register operands
-operand regD()
-%{
-  constraint(ALLOC_IN_RC(double_reg));
-  match(RegD);
+operand vecD() %{
+  constraint(ALLOC_IN_RC(vectord_reg));
+  match(VecD);
+
+  format %{ %}
+  interface(REG_INTER);
+%}
+
+operand vecX() %{
+  constraint(ALLOC_IN_RC(vectorx_reg));
+  match(VecX);
+
+  format %{ %}
+  interface(REG_INTER);
+%}
+
+operand vecY() %{
+  constraint(ALLOC_IN_RC(vectory_reg));
+  match(VecY);
 
   format %{ %}
   interface(REG_INTER);
@@ -4947,7 +4994,7 @@
 %}
 
 // Load Unsigned Integer into Long Register
-instruct loadUI2L(rRegL dst, memory mem, immL_32bits mask) 
+instruct loadUI2L(rRegL dst, memory mem, immL_32bits mask)
 %{
   match(Set dst (AndL (ConvI2L (LoadI mem)) mask));
 
@@ -10374,7 +10421,7 @@
 
   format %{ "xorq    rax, rax\t# ClearArray:\n\t"
             "rep     stosq\t# Store rax to *rdi++ while rcx--" %}
-  ins_encode %{ 
+  ins_encode %{
     __ clear_mem($base$$Register, $cnt$$Register, $zero$$Register);
   %}
   ins_pipe(pipe_slow);
@@ -10389,7 +10436,7 @@
   format %{ "xorq    rax, rax\t# ClearArray:\n\t"
             "shlq    rcx,3\t# Convert doublewords to bytes\n\t"
             "rep     stosb\t# Store rax to *rdi++ while rcx--" %}
-  ins_encode %{ 
+  ins_encode %{
     __ clear_mem($base$$Register, $cnt$$Register, $zero$$Register);
   %}
   ins_pipe( pipe_slow );
--- a/hotspot/src/cpu/zero/vm/entry_zero.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/zero/vm/entry_zero.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -26,6 +26,8 @@
 #ifndef CPU_ZERO_VM_ENTRY_ZERO_HPP
 #define CPU_ZERO_VM_ENTRY_ZERO_HPP
 
+#include "interpreter/cppInterpreter.hpp"
+
 class ZeroEntry {
  public:
   ZeroEntry() {
--- a/hotspot/src/cpu/zero/vm/nativeInst_zero.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/cpu/zero/vm/nativeInst_zero.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -25,6 +25,8 @@
 
 #include "precompiled.hpp"
 #include "assembler_zero.inline.hpp"
+#include "entry_zero.hpp"
+#include "interpreter/cppInterpreter.hpp"
 #include "memory/resourceArea.hpp"
 #include "nativeInst_zero.hpp"
 #include "oops/oop.inline.hpp"
--- a/hotspot/src/os/linux/vm/os_linux.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/os/linux/vm/os_linux.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -3474,25 +3474,69 @@
   return addr;
 }
 
+// Helper for os::Linux::reserve_memory_special_huge_tlbfs_mixed().
+// Allocate (using mmap, NO_RESERVE, with small pages) at either a given request address
+//   (req_addr != NULL) or with a given alignment.
+//  - bytes shall be a multiple of alignment.
+//  - req_addr can be NULL. If not NULL, it must be a multiple of alignment.
+//  - alignment sets the alignment at which memory shall be allocated.
+//     It must be a multiple of allocation granularity.
+// Returns address of memory or NULL. If req_addr was not NULL, will only return
+//  req_addr or NULL.
+static char* anon_mmap_aligned(size_t bytes, size_t alignment, char* req_addr) {
+
+  size_t extra_size = bytes;
+  if (req_addr == NULL && alignment > 0) {
+    extra_size += alignment;
+  }
+
+  char* start = (char*) ::mmap(req_addr, extra_size, PROT_NONE,
+    MAP_PRIVATE|MAP_ANONYMOUS|MAP_NORESERVE,
+    -1, 0);
+  if (start == MAP_FAILED) {
+    start = NULL;
+  } else {
+    if (req_addr != NULL) {
+      if (start != req_addr) {
+        ::munmap(start, extra_size);
+        start = NULL;
+      }
+    } else {
+      char* const start_aligned = (char*) align_ptr_up(start, alignment);
+      char* const end_aligned = start_aligned + bytes;
+      char* const end = start + extra_size;
+      if (start_aligned > start) {
+        ::munmap(start, start_aligned - start);
+      }
+      if (end_aligned < end) {
+        ::munmap(end_aligned, end - end_aligned);
+      }
+      start = start_aligned;
+    }
+  }
+  return start;
+
+}
+
+// Reserve memory using mmap(MAP_HUGETLB).
+//  - bytes shall be a multiple of alignment.
+//  - req_addr can be NULL. If not NULL, it must be a multiple of alignment.
+//  - alignment sets the alignment at which memory shall be allocated.
+//     It must be a multiple of allocation granularity.
+// Returns address of memory or NULL. If req_addr was not NULL, will only return
+//  req_addr or NULL.
 char* os::Linux::reserve_memory_special_huge_tlbfs_mixed(size_t bytes,
                                                          size_t alignment,
                                                          char* req_addr,
                                                          bool exec) {
   size_t large_page_size = os::large_page_size();
-
   assert(bytes >= large_page_size, "Shouldn't allocate large pages for small sizes");
 
-  // Allocate small pages.
-
-  char* start;
-  if (req_addr != NULL) {
-    assert(is_ptr_aligned(req_addr, alignment), "Must be");
-    assert(is_size_aligned(bytes, alignment), "Must be");
-    start = os::reserve_memory(bytes, req_addr);
-    assert(start == NULL || start == req_addr, "Must be");
-  } else {
-    start = os::reserve_memory_aligned(bytes, alignment);
-  }
+  assert(is_ptr_aligned(req_addr, alignment), "Must be");
+  assert(is_size_aligned(bytes, alignment), "Must be");
+
+  // First reserve - but not commit - the address range in small pages.
+  char* const start = anon_mmap_aligned(bytes, alignment, req_addr);
 
   if (start == NULL) {
     return NULL;
@@ -3500,13 +3544,6 @@
 
   assert(is_ptr_aligned(start, alignment), "Must be");
 
-  if (MemTracker::tracking_level() > NMT_minimal) {
-    // os::reserve_memory_special will record this memory area.
-    // Need to release it here to prevent overlapping reservations.
-    Tracker tkr = MemTracker::get_virtual_memory_release_tracker();
-    tkr.record((address)start, bytes);
-  }
-
   char* end = start + bytes;
 
   // Find the regions of the allocated chunk that can be promoted to large pages.
@@ -3526,9 +3563,9 @@
 
   int prot = exec ? PROT_READ|PROT_WRITE|PROT_EXEC : PROT_READ|PROT_WRITE;
 
-
   void* result;
 
+  // Commit small-paged leading area.
   if (start != lp_start) {
     result = ::mmap(start, lp_start - start, prot,
                     MAP_PRIVATE|MAP_ANONYMOUS|MAP_FIXED,
@@ -3539,11 +3576,12 @@
     }
   }
 
+  // Commit large-paged area.
   result = ::mmap(lp_start, lp_bytes, prot,
                   MAP_PRIVATE|MAP_ANONYMOUS|MAP_FIXED|MAP_HUGETLB,
                   -1, 0);
   if (result == MAP_FAILED) {
-    warn_on_large_pages_failure(req_addr, bytes, errno);
+    warn_on_large_pages_failure(lp_start, lp_bytes, errno);
     // If the mmap above fails, the large pages region will be unmapped and we
     // have regions before and after with small pages. Release these regions.
     //
@@ -3556,6 +3594,7 @@
     return NULL;
   }
 
+  // Commit small-paged trailing area.
   if (lp_end != end) {
     result = ::mmap(lp_end, end - lp_end, prot,
                     MAP_PRIVATE|MAP_ANONYMOUS|MAP_FIXED,
@@ -3575,7 +3614,7 @@
                                                    bool exec) {
   assert(UseLargePages && UseHugeTLBFS, "only for Huge TLBFS large pages");
   assert(is_ptr_aligned(req_addr, alignment), "Must be");
-  assert(is_power_of_2(alignment), "Must be");
+  assert(is_size_aligned(alignment, os::vm_allocation_granularity()), "Must be");
   assert(is_power_of_2(os::large_page_size()), "Must be");
   assert(bytes >= os::large_page_size(), "Shouldn't allocate large pages for small sizes");
 
@@ -4760,8 +4799,8 @@
             FLAG_IS_DEFAULT(UseSHM) &&
             FLAG_IS_DEFAULT(UseHugeTLBFS)) {
           UseLargePages = false;
-        } else {
-          warning("UseNUMA is not fully compatible with SHM/HugeTLBFS large pages, disabling adaptive resizing");
+        } else if (UseAdaptiveSizePolicy || UseAdaptiveNUMAChunkSizing) {
+          warning("UseNUMA is not fully compatible with SHM/HugeTLBFS large pages, disabling adaptive resizing (-XX:-UseAdaptiveSizePolicy -XX:-UseAdaptiveNUMAChunkSizing)");
           UseAdaptiveSizePolicy = false;
           UseAdaptiveNUMAChunkSizing = false;
         }
@@ -6086,47 +6125,100 @@
     }
   }
 
-  static void test_reserve_memory_special_huge_tlbfs_mixed(size_t size, size_t alignment) {
-    if (!UseHugeTLBFS) {
-      return;
-    }
-
-    test_log("test_reserve_memory_special_huge_tlbfs_mixed(" SIZE_FORMAT ", " SIZE_FORMAT ")",
-             size, alignment);
-
-    assert(size >= os::large_page_size(), "Incorrect input to test");
-
-    char* addr = os::Linux::reserve_memory_special_huge_tlbfs_mixed(size, alignment, NULL, false);
-
-    if (addr != NULL) {
-      small_page_write(addr, size);
-
-      os::Linux::release_memory_special_huge_tlbfs(addr, size);
-    }
-  }
-
-  static void test_reserve_memory_special_huge_tlbfs_mixed_all_alignments(size_t size) {
-    size_t lp = os::large_page_size();
-    size_t ag = os::vm_allocation_granularity();
-
-    for (size_t alignment = ag; is_size_aligned(size, alignment); alignment *= 2) {
-      test_reserve_memory_special_huge_tlbfs_mixed(size, alignment);
-    }
-  }
-
   static void test_reserve_memory_special_huge_tlbfs_mixed() {
     size_t lp = os::large_page_size();
     size_t ag = os::vm_allocation_granularity();
 
-    test_reserve_memory_special_huge_tlbfs_mixed_all_alignments(lp);
-    test_reserve_memory_special_huge_tlbfs_mixed_all_alignments(lp + ag);
-    test_reserve_memory_special_huge_tlbfs_mixed_all_alignments(lp + lp / 2);
-    test_reserve_memory_special_huge_tlbfs_mixed_all_alignments(lp * 2);
-    test_reserve_memory_special_huge_tlbfs_mixed_all_alignments(lp * 2 + ag);
-    test_reserve_memory_special_huge_tlbfs_mixed_all_alignments(lp * 2 - ag);
-    test_reserve_memory_special_huge_tlbfs_mixed_all_alignments(lp * 2 + lp / 2);
-    test_reserve_memory_special_huge_tlbfs_mixed_all_alignments(lp * 10);
-    test_reserve_memory_special_huge_tlbfs_mixed_all_alignments(lp * 10 + lp / 2);
+    // sizes to test
+    const size_t sizes[] = {
+      lp, lp + ag, lp + lp / 2, lp * 2,
+      lp * 2 + ag, lp * 2 - ag, lp * 2 + lp / 2,
+      lp * 10, lp * 10 + lp / 2
+    };
+    const int num_sizes = sizeof(sizes) / sizeof(size_t);
+
+    // For each size/alignment combination, we test three scenarios:
+    // 1) with req_addr == NULL
+    // 2) with a non-null req_addr at which we expect to successfully allocate
+    // 3) with a non-null req_addr which contains a pre-existing mapping, at which we
+    //    expect the allocation to either fail or to ignore req_addr
+
+    // Pre-allocate two areas; they shall be as large as the largest allocation
+    //  and aligned to the largest alignment we will be testing.
+    const size_t mapping_size = sizes[num_sizes - 1] * 2;
+    char* const mapping1 = (char*) ::mmap(NULL, mapping_size,
+      PROT_NONE, MAP_PRIVATE|MAP_ANONYMOUS|MAP_NORESERVE,
+      -1, 0);
+    assert(mapping1 != MAP_FAILED, "should work");
+
+    char* const mapping2 = (char*) ::mmap(NULL, mapping_size,
+      PROT_NONE, MAP_PRIVATE|MAP_ANONYMOUS|MAP_NORESERVE,
+      -1, 0);
+    assert(mapping2 != MAP_FAILED, "should work");
+
+    // Unmap the first mapping, but leave the second mapping intact: the first
+    // mapping will serve as a value for a "good" req_addr (case 2). The second
+    // mapping, still intact, as "bad" req_addr (case 3).
+    ::munmap(mapping1, mapping_size);
+
+    // Case 1
+    test_log("%s, req_addr NULL:", __FUNCTION__);
+    test_log("size            align           result");
+
+    for (int i = 0; i < num_sizes; i++) {
+      const size_t size = sizes[i];
+      for (size_t alignment = ag; is_size_aligned(size, alignment); alignment *= 2) {
+        char* p = os::Linux::reserve_memory_special_huge_tlbfs_mixed(size, alignment, NULL, false);
+        test_log(SIZE_FORMAT_HEX " " SIZE_FORMAT_HEX " ->  " PTR_FORMAT " %s",
+            size, alignment, p, (p != NULL ? "" : "(failed)"));
+        if (p != NULL) {
+          assert(is_ptr_aligned(p, alignment), "must be");
+          small_page_write(p, size);
+          os::Linux::release_memory_special_huge_tlbfs(p, size);
+        }
+      }
+    }
+
+    // Case 2
+    test_log("%s, req_addr non-NULL:", __FUNCTION__);
+    test_log("size            align           req_addr         result");
+
+    for (int i = 0; i < num_sizes; i++) {
+      const size_t size = sizes[i];
+      for (size_t alignment = ag; is_size_aligned(size, alignment); alignment *= 2) {
+        char* const req_addr = (char*) align_ptr_up(mapping1, alignment);
+        char* p = os::Linux::reserve_memory_special_huge_tlbfs_mixed(size, alignment, req_addr, false);
+        test_log(SIZE_FORMAT_HEX " " SIZE_FORMAT_HEX " " PTR_FORMAT " ->  " PTR_FORMAT " %s",
+            size, alignment, req_addr, p,
+            ((p != NULL ? (p == req_addr ? "(exact match)" : "") : "(failed)")));
+        if (p != NULL) {
+          assert(p == req_addr, "must be");
+          small_page_write(p, size);
+          os::Linux::release_memory_special_huge_tlbfs(p, size);
+        }
+      }
+    }
+
+    // Case 3
+    test_log("%s, req_addr non-NULL with preexisting mapping:", __FUNCTION__);
+    test_log("size            align           req_addr         result");
+
+    for (int i = 0; i < num_sizes; i++) {
+      const size_t size = sizes[i];
+      for (size_t alignment = ag; is_size_aligned(size, alignment); alignment *= 2) {
+        char* const req_addr = (char*) align_ptr_up(mapping2, alignment);
+        char* p = os::Linux::reserve_memory_special_huge_tlbfs_mixed(size, alignment, req_addr, false);
+        test_log(SIZE_FORMAT_HEX " " SIZE_FORMAT_HEX " " PTR_FORMAT " ->  " PTR_FORMAT " %s",
+            size, alignment, req_addr, p,
+            ((p != NULL ? "" : "(failed)")));
+        // as the area around req_addr contains already existing mappings, the API should always
+        // return NULL (as per contract, it cannot return another address)
+        assert(p == NULL, "must be");
+      }
+    }
+
+    ::munmap(mapping2, mapping_size);
+
   }
 
   static void test_reserve_memory_special_huge_tlbfs() {
--- a/hotspot/src/share/tools/IdealGraphVisualizer/BatikSVGProxy/nbproject/build-impl.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/BatikSVGProxy/nbproject/build-impl.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -4,6 +4,13 @@
 ***         EDIT ../build.xml INSTEAD         ***
 -->
 <project name="com.sun.hotspot.igv.svg-impl" basedir="..">
+    <fail message="Please build using Ant 1.7.1 or higher.">
+        <condition>
+            <not>
+                <antversion atleast="1.7.1"/>
+            </not>
+        </condition>
+    </fail>
     <property file="nbproject/private/suite-private.properties"/>
     <property file="nbproject/suite.properties"/>
     <fail unless="suite.dir">You must set 'suite.dir' to point to your containing module suite</fail>
@@ -16,13 +23,21 @@
             <property name="@{name}" value="${@{value}}"/>
         </sequential>
     </macrodef>
+    <macrodef name="evalprops" uri="http://www.netbeans.org/ns/nb-module-project/2">
+        <attribute name="property"/>
+        <attribute name="value"/>
+        <sequential>
+            <property name="@{property}" value="@{value}"/>
+        </sequential>
+    </macrodef>
     <property file="${user.properties.file}"/>
     <nbmproject2:property name="harness.dir" value="nbplatform.${nbplatform.active}.harness.dir" xmlns:nbmproject2="http://www.netbeans.org/ns/nb-module-project/2"/>
-    <nbmproject2:property name="netbeans.dest.dir" value="nbplatform.${nbplatform.active}.netbeans.dest.dir" xmlns:nbmproject2="http://www.netbeans.org/ns/nb-module-project/2"/>
-    <fail message="You must define 'nbplatform.${nbplatform.active}.harness.dir'">
+    <nbmproject2:property name="nbplatform.active.dir" value="nbplatform.${nbplatform.active}.netbeans.dest.dir" xmlns:nbmproject2="http://www.netbeans.org/ns/nb-module-project/2"/>
+    <nbmproject2:evalprops property="cluster.path.evaluated" value="${cluster.path}" xmlns:nbmproject2="http://www.netbeans.org/ns/nb-module-project/2"/>
+    <fail message="Path to 'platform' cluster missing in $${cluster.path} property or using corrupt Netbeans Platform (missing harness).">
         <condition>
             <not>
-                <available file="${harness.dir}" type="dir"/>
+                <contains string="${cluster.path.evaluated}" substring="platform"/>
             </not>
         </condition>
     </fail>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/BatikSVGProxy/nbproject/genfiles.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/BatikSVGProxy/nbproject/genfiles.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,8 +1,5 @@
-build.xml.data.CRC32=ebcf0422
-build.xml.script.CRC32=d7a2678d
-build.xml.stylesheet.CRC32=79c3b980
 # This file is used by a NetBeans-based IDE to track changes in generated files such as build-impl.xml.
 # Do not edit this file. You may delete it but then the IDE will never regenerate such files for you.
 nbproject/build-impl.xml.data.CRC32=ebcf0422
-nbproject/build-impl.xml.script.CRC32=57997f94
-nbproject/build-impl.xml.stylesheet.CRC32=deb65f65
+nbproject/build-impl.xml.script.CRC32=42ef3ff6
+nbproject/build-impl.xml.stylesheet.CRC32=238281d1@2.47.1
--- a/hotspot/src/share/tools/IdealGraphVisualizer/BatikSVGProxy/nbproject/project.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/BatikSVGProxy/nbproject/project.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,2 +1,2 @@
-javac.source=1.5
-javac.compilerargs=-Xlint -Xlint:-serial
+javac.source=1.7
+javac.compilerargs=-Xlint -Xlint:-serial
--- a/hotspot/src/share/tools/IdealGraphVisualizer/BatikSVGProxy/src/com/sun/hotspot/igv/svg/BatikSVG.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/BatikSVGProxy/src/com/sun/hotspot/igv/svg/BatikSVG.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -25,40 +25,58 @@
 
 import java.awt.Graphics2D;
 import java.io.Writer;
+import java.io.File;
 import java.lang.reflect.Constructor;
 import java.lang.reflect.InvocationTargetException;
 import java.lang.reflect.Method;
+import java.net.MalformedURLException;
+import java.net.URL;
+import java.net.URLClassLoader;
 import org.w3c.dom.DOMImplementation;
 
 /**
- *
+ * Utility class
  * @author Thomas Wuerthinger
  */
 public class BatikSVG {
 
+    private BatikSVG() {
+    }
+
     private static Constructor SVGGraphics2DConstructor;
-    private static Method Method_stream;
-    private static Method Method_createDefault;
-    private static Method Method_getDOMImplementation;
-    private static Method Method_setEmbeddedFontsOn;
+    private static Method streamMethod;
+    private static Method createDefaultMethod;
+    private static Method getDOMImplementationMethod;
+    private static Method setEmbeddedFontsOnMethod;
+    private static Class<?> classSVGGraphics2D;
 
+    /**
+     * Creates a graphics object that allows to be exported to SVG data using the {@link #printToStream(Graphics2D, Writer, boolean) printToStream} method.
+     * @return the newly created Graphics2D object or null if the library does not exist
+     */
     public static Graphics2D createGraphicsObject() {
         try {
             if (SVGGraphics2DConstructor == null) {
-                ClassLoader cl = BatikSVG.class.getClassLoader();
-                Class Class_GenericDOMImplementation = cl.loadClass("org.apache.batik.dom.GenericDOMImplementation");
-                Class Class_SVGGeneratorContext = cl.loadClass("org.apache.batik.svggen.SVGGeneratorContext");
-                Class Class_SVGGraphics2D = cl.loadClass("org.apache.batik.svggen.SVGGraphics2D");
-                Method_getDOMImplementation = Class_GenericDOMImplementation.getDeclaredMethod("getDOMImplementation", new Class[0]);
-                Method_createDefault = Class_SVGGeneratorContext.getDeclaredMethod("createDefault", new Class[]{org.w3c.dom.Document.class});
-                Method_setEmbeddedFontsOn = Class_SVGGeneratorContext.getDeclaredMethod("setEmbeddedFontsOn", new Class[]{boolean.class});
-                Method_stream = Class_SVGGraphics2D.getDeclaredMethod("stream", Writer.class, boolean.class);
-                SVGGraphics2DConstructor = Class_SVGGraphics2D.getConstructor(Class_SVGGeneratorContext, boolean.class);
+                String batikJar = System.getenv().get("IGV_BATIK_JAR");
+                if (batikJar == null) {
+                    return null;
+                }
+                // Load batik in it's own class loader since some it's support jars interfere with the JDK
+                URL url = new File(batikJar).toURI().toURL();
+                ClassLoader cl = new URLClassLoader(new URL[] { url });
+                Class<?> classGenericDOMImplementation = cl.loadClass("org.apache.batik.dom.GenericDOMImplementation");
+                Class<?> classSVGGeneratorContext = cl.loadClass("org.apache.batik.svggen.SVGGeneratorContext");
+                classSVGGraphics2D = cl.loadClass("org.apache.batik.svggen.SVGGraphics2D");
+                getDOMImplementationMethod = classGenericDOMImplementation.getDeclaredMethod("getDOMImplementation", new Class[0]);
+                createDefaultMethod = classSVGGeneratorContext.getDeclaredMethod("createDefault", new Class[]{org.w3c.dom.Document.class});
+                setEmbeddedFontsOnMethod = classSVGGeneratorContext.getDeclaredMethod("setEmbeddedFontsOn", new Class[]{boolean.class});
+                streamMethod = classSVGGraphics2D.getDeclaredMethod("stream", Writer.class, boolean.class);
+                SVGGraphics2DConstructor = classSVGGraphics2D.getConstructor(classSVGGeneratorContext, boolean.class);
             }
-            DOMImplementation dom = (DOMImplementation) Method_getDOMImplementation.invoke(null);
+            DOMImplementation dom = (DOMImplementation) getDOMImplementationMethod.invoke(null);
             org.w3c.dom.Document document = dom.createDocument("http://www.w3.org/2000/svg", "svg", null);
-            Object ctx = Method_createDefault.invoke(null, document);
-            Method_setEmbeddedFontsOn.invoke(ctx, true);
+            Object ctx = createDefaultMethod.invoke(null, document);
+            setEmbeddedFontsOnMethod.invoke(ctx, true);
             Graphics2D svgGenerator = (Graphics2D) SVGGraphics2DConstructor.newInstance(ctx, true);
             return svgGenerator;
         } catch (ClassNotFoundException e) {
@@ -71,12 +89,22 @@
             return null;
         } catch (InstantiationException e) {
             return null;
+        } catch (MalformedURLException e) {
+            return null;
         }
     }
 
+    /**
+     * Serializes a graphics object to a stream in SVG format.
+     * @param svgGenerator the graphics object. Only graphics objects created by the {@link #createGraphicsObject() createGraphicsObject} method are valid.
+     * @param stream the stream to which the data is written
+     * @param useCSS whether to use CSS styles in the SVG output
+     */
     public static void printToStream(Graphics2D svgGenerator, Writer stream, boolean useCSS) {
+        assert classSVGGraphics2D != null;
+        assert classSVGGraphics2D.isInstance(svgGenerator);
         try {
-            Method_stream.invoke(svgGenerator, stream, useCSS);
+            streamMethod.invoke(svgGenerator, stream, useCSS);
         } catch (IllegalAccessException e) {
             assert false;
         } catch (InvocationTargetException e) {
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/BatikSVGProxy/src/com/sun/hotspot/igv/svg/package-info.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,29 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+/**
+ * This package is used to proxy the SVG export functionality of the BatikSVG library. Reflection is used such that the
+ * library is optional and need not be present at build time.
+ */
+package com.sun.hotspot.igv.svg;
+
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/manifest.mf	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/manifest.mf	Wed Jul 05 20:35:10 2017 +0200
@@ -1,6 +1,6 @@
-Manifest-Version: 1.0
-OpenIDE-Module: com.sun.hotspot.igv.bytecodes
-OpenIDE-Module-Layer: com/sun/hotspot/igv/bytecodes/layer.xml
-OpenIDE-Module-Localizing-Bundle: com/sun/hotspot/igv/bytecodes/Bundle.properties
-OpenIDE-Module-Specification-Version: 1.0
-
+Manifest-Version: 1.0
+OpenIDE-Module: com.sun.hotspot.igv.bytecodes
+OpenIDE-Module-Layer: com/sun/hotspot/igv/bytecodes/layer.xml
+OpenIDE-Module-Localizing-Bundle: com/sun/hotspot/igv/bytecodes/Bundle.properties
+OpenIDE-Module-Specification-Version: 1.0
+
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/nbproject/project.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/nbproject/project.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,2 +1,2 @@
-javac.source=1.5
-javac.compilerargs=-Xlint -Xlint:-serial
+javac.source=1.7
+javac.compilerargs=-Xlint -Xlint:-serial
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/nbproject/project.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/nbproject/project.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -15,12 +15,36 @@
                     </run-dependency>
                 </dependency>
                 <dependency>
+                    <code-name-base>com.sun.hotspot.igv.graph</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>1.0</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>com.sun.hotspot.igv.util</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>1.0</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
                     <code-name-base>org.jdesktop.layout</code-name-base>
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
                         <release-version>1</release-version>
-                        <specification-version>1.4</specification-version>
+                        <specification-version>1.16.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.awt</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>7.39.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -28,7 +52,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>6.11</specification-version>
+                        <specification-version>6.34.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -36,7 +60,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>7.2.0.1</specification-version>
+                        <specification-version>7.20.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -44,7 +68,15 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>7.9.0.1</specification-version>
+                        <specification-version>8.14.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.util.lookup</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>8.6.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -52,7 +84,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>6.16</specification-version>
+                        <specification-version>6.39.1</specification-version>
                     </run-dependency>
                 </dependency>
             </module-dependencies>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/Bundle.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/Bundle.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
-CTL_BytecodeViewAction=Open BytecodeView Window
-CTL_BytecodeViewTopComponent=BytecodeView Window
+CTL_BytecodeViewAction=Bytecode
+CTL_BytecodeViewTopComponent=Bytecode
 CTL_SelectBytecodesAction=Select nodes
-HINT_BytecodeViewTopComponent=This is a BytecodeView window
+HINT_BytecodeViewTopComponent=Shows the bytecode associated with the displayed graph.
 OpenIDE-Module-Name=Bytecodes
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/BytecodeNode.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/BytecodeNode.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -29,14 +29,14 @@
 import com.sun.hotspot.igv.data.Properties;
 import com.sun.hotspot.igv.data.Properties.StringPropertyMatcher;
 import java.awt.Image;
-import java.util.HashSet;
+import java.util.LinkedHashSet;
 import java.util.List;
 import java.util.Set;
 import javax.swing.Action;
 import org.openide.nodes.AbstractNode;
 import org.openide.nodes.Children;
 import org.openide.nodes.Node;
-import org.openide.util.Utilities;
+import org.openide.util.ImageUtilities;
 
 /**
  *
@@ -49,29 +49,35 @@
     public BytecodeNode(InputBytecode bytecode, InputGraph graph, String bciValue) {
 
         super(Children.LEAF);
-        this.setDisplayName(bytecode.getBci() + " " + bytecode.getName());
+        String displayName = bytecode.getBci() + " " + bytecode.getName() + " " + bytecode.getOperands();
 
         bciValue = bytecode.getBci() + " " + bciValue;
         bciValue = bciValue.trim();
 
-        Properties.PropertySelector<InputNode> selector = new Properties.PropertySelector<InputNode>(graph.getNodes());
+        Properties.PropertySelector<InputNode> selector = new Properties.PropertySelector<>(graph.getNodes());
         StringPropertyMatcher matcher = new StringPropertyMatcher("bci", bciValue);
         List<InputNode> nodeList = selector.selectMultiple(matcher);
         if (nodeList.size() > 0) {
-            nodes = new HashSet<InputNode>();
+            nodes = new LinkedHashSet<>();
             for (InputNode n : nodeList) {
                 nodes.add(n);
             }
-            this.setDisplayName(this.getDisplayName() + " (" + nodes.size() + " nodes)");
+            displayName += " (" + nodes.size() + " nodes)";
         }
+
+        if (bytecode.getComment() != null) {
+            displayName += " // " + bytecode.getComment();
+        }
+
+        this.setDisplayName(displayName);
     }
 
     @Override
     public Image getIcon(int i) {
         if (nodes != null) {
-            return Utilities.loadImage("com/sun/hotspot/igv/bytecodes/images/link.gif");
+            return ImageUtilities.loadImage("com/sun/hotspot/igv/bytecodes/images/link.png");
         } else {
-            return Utilities.loadImage("com/sun/hotspot/igv/bytecodes/images/bytecode.gif");
+            return ImageUtilities.loadImage("com/sun/hotspot/igv/bytecodes/images/bytecode.png");
         }
     }
 
@@ -91,6 +97,7 @@
     }
 
     @Override
+    @SuppressWarnings("unchecked")
     public <T extends Node.Cookie> T getCookie(Class<T> aClass) {
         if (aClass == SelectBytecodesCookie.class && nodes != null) {
             return (T) (new SelectBytecodesCookie(nodes));
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/BytecodeViewAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/BytecodeViewAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -37,6 +37,7 @@
         super(NbBundle.getMessage(BytecodeViewAction.class, "CTL_BytecodeViewAction"));
     }
 
+    @Override
     public void actionPerformed(ActionEvent evt) {
         TopComponent win = BytecodeViewTopComponent.findInstance();
         win.open();
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/BytecodeViewTopComponent.form	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/BytecodeViewTopComponent.form	Wed Jul 05 20:35:10 2017 +0200
@@ -3,6 +3,8 @@
 <Form version="1.3" maxVersion="1.3" type="org.netbeans.modules.form.forminfo.JPanelFormInfo">
   <AuxValues>
     <AuxValue name="FormSettings_autoResourcing" type="java.lang.Integer" value="0"/>
+    <AuxValue name="FormSettings_autoSetComponentName" type="java.lang.Boolean" value="false"/>
+    <AuxValue name="FormSettings_generateFQN" type="java.lang.Boolean" value="true"/>
     <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="true"/>
     <AuxValue name="FormSettings_i18nAutoMode" type="java.lang.Boolean" value="false"/>
     <AuxValue name="FormSettings_layoutCodeTarget" type="java.lang.Integer" value="2"/>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/BytecodeViewTopComponent.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/BytecodeViewTopComponent.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -26,6 +26,7 @@
 import com.sun.hotspot.igv.data.Group;
 import com.sun.hotspot.igv.data.InputGraph;
 import com.sun.hotspot.igv.data.services.InputGraphProvider;
+import com.sun.hotspot.igv.util.LookupHistory;
 import java.awt.BorderLayout;
 import java.io.Serializable;
 import javax.swing.SwingUtilities;
@@ -33,11 +34,7 @@
 import org.openide.explorer.ExplorerManager;
 import org.openide.explorer.ExplorerUtils;
 import org.openide.explorer.view.BeanTreeView;
-import org.openide.util.Lookup;
-import org.openide.util.LookupEvent;
-import org.openide.util.LookupListener;
-import org.openide.util.NbBundle;
-import org.openide.util.Utilities;
+import org.openide.util.*;
 import org.openide.windows.TopComponent;
 import org.openide.windows.WindowManager;
 
@@ -91,6 +88,7 @@
     }// </editor-fold>//GEN-END:initComponents
     // Variables declaration - do not modify//GEN-BEGIN:variables
     // End of variables declaration//GEN-END:variables
+
     /**
      * Gets default instance. Do not use directly: reserved for *.settings files only,
      * i.e. deserialization routines; otherwise you could get a non-deserialized instance.
@@ -126,7 +124,7 @@
 
     @Override
     public void componentOpened() {
-        Lookup.Template tpl = new Lookup.Template(Object.class);
+        Lookup.Template<InputGraphProvider> tpl = new Lookup.Template<>(InputGraphProvider.class);
         result = Utilities.actionsGlobalContext().lookup(tpl);
         result.addLookupListener(this);
     }
@@ -147,23 +145,47 @@
         return PREFERRED_ID;
     }
 
+    @Override
     public ExplorerManager getExplorerManager() {
         return manager;
     }
 
+    @Override
+    public void requestActive() {
+        super.requestActive();
+        this.treeView.requestFocus();
+    }
+
+    @Override
+    public boolean requestFocus(boolean temporary) {
+        this.treeView.requestFocus();
+        return super.requestFocus(temporary);
+    }
+
+    @Override
+    protected boolean requestFocusInWindow(boolean temporary) {
+        this.treeView.requestFocus();
+        return super.requestFocusInWindow(temporary);
+    }
+
+    @Override
     public void resultChanged(LookupEvent lookupEvent) {
-        final InputGraphProvider p = Lookup.getDefault().lookup(InputGraphProvider.class);
-        if (p != null) {
+        final InputGraphProvider p = LookupHistory.getLast(InputGraphProvider.class);//)Utilities.actionsGlobalContext().lookup(InputGraphProvider.class);
             SwingUtilities.invokeLater(new Runnable() {
+                @Override
                 public void run() {
-            InputGraph graph = p.getGraph();
-            if (graph != null) {
-                Group g = graph.getGroup();
-                rootNode.update(graph, g.getMethod());
-            }
-        }
+                if (p != null) {
+                    InputGraph graph = p.getGraph();
+                    if (graph != null) {
+                        Group g = graph.getGroup();
+                        rootNode.update(graph, g.getMethod());
+                        return;
+                    }
+                }
+                        rootNode.update(null, null);
+                    }
             });
-        }
+
     }
 
     final static class ResolvableHelper implements Serializable {
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/MethodNode.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/MethodNode.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -30,7 +30,7 @@
 import org.openide.nodes.AbstractNode;
 import org.openide.nodes.Children;
 import org.openide.nodes.Node;
-import org.openide.util.Utilities;
+import org.openide.util.ImageUtilities;
 
 /**
  *
@@ -38,7 +38,7 @@
  */
 public class MethodNode extends AbstractNode {
 
-    private static class MethodNodeChildren extends Children.Keys {
+    private static class MethodNodeChildren extends Children.Keys<InputBytecode> {
 
         private InputMethod method;
         private InputGraph graph;
@@ -50,9 +50,8 @@
             this.graph = graph;
         }
 
-        protected Node[] createNodes(Object object) {
-            assert object instanceof InputBytecode;
-            InputBytecode bc = (InputBytecode) object;
+        @Override
+        protected Node[] createNodes(InputBytecode bc) {
             if (bc.getInlined() == null) {
                 return new Node[]{new BytecodeNode(bc, graph, bciString)};
             } else {
@@ -84,7 +83,7 @@
 
     @Override
     public Image getIcon(int i) {
-        return Utilities.loadImage("com/sun/hotspot/igv/bytecodes/images/method.gif");
+        return ImageUtilities.loadImage("com/sun/hotspot/igv/bytecodes/images/method.png");
     }
 
     @Override
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/SelectBytecodesAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/SelectBytecodesAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -24,9 +24,9 @@
 package com.sun.hotspot.igv.bytecodes;
 
 import com.sun.hotspot.igv.data.services.InputGraphProvider;
+import com.sun.hotspot.igv.util.LookupHistory;
 import org.openide.nodes.Node;
 import org.openide.util.HelpCtx;
-import org.openide.util.Lookup;
 import org.openide.util.NbBundle;
 import org.openide.util.actions.CookieAction;
 
@@ -36,22 +36,26 @@
  */
 public final class SelectBytecodesAction extends CookieAction {
 
+    @Override
     protected void performAction(Node[] activatedNodes) {
         SelectBytecodesCookie c = activatedNodes[0].getCookie(SelectBytecodesCookie.class);
-        InputGraphProvider p = Lookup.getDefault().lookup(InputGraphProvider.class);
+        InputGraphProvider p = LookupHistory.getLast(InputGraphProvider.class);//Utilities.actionsGlobalContext().lookup(InputGraphProvider.class);
         if (p != null) {
             p.setSelectedNodes(c.getNodes());
         }
     }
 
+    @Override
     protected int mode() {
         return CookieAction.MODE_EXACTLY_ONE;
     }
 
+    @Override
     public String getName() {
         return NbBundle.getMessage(SelectBytecodesAction.class, "CTL_SelectBytecodesAction");
     }
 
+    @Override
     protected Class[] cookieClasses() {
         return new Class[]{
             SelectBytecodesCookie.class
@@ -64,6 +68,7 @@
         putValue("noIconInMenu", Boolean.TRUE);
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
@@ -73,3 +78,4 @@
         return false;
     }
 }
+
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/SelectBytecodesCookie.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/SelectBytecodesCookie.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/images/bytecode.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/images/bytecode.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/images/link.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/images/link.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/images/method.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Bytecodes/src/com/sun/hotspot/igv/bytecodes/images/method.png has changed
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/manifest.mf	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/manifest.mf	Wed Jul 05 20:35:10 2017 +0200
@@ -1,6 +1,6 @@
-Manifest-Version: 1.0
-OpenIDE-Module: com.sun.hotspot.igv.controlflow
-OpenIDE-Module-Layer: com/sun/hotspot/igv/controlflow/layer.xml
-OpenIDE-Module-Localizing-Bundle: com/sun/hotspot/igv/controlflow/Bundle.properties
-OpenIDE-Module-Specification-Version: 1.0
-
+Manifest-Version: 1.0
+OpenIDE-Module: com.sun.hotspot.igv.controlflow
+OpenIDE-Module-Layer: com/sun/hotspot/igv/controlflow/layer.xml
+OpenIDE-Module-Localizing-Bundle: com/sun/hotspot/igv/controlflow/Bundle.properties
+OpenIDE-Module-Specification-Version: 1.0
+
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/nbproject/project.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/nbproject/project.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -31,12 +31,20 @@
                     </run-dependency>
                 </dependency>
                 <dependency>
+                    <code-name-base>com.sun.hotspot.igv.util</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>1.0</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
                     <code-name-base>org.jdesktop.layout</code-name-base>
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
                         <release-version>1</release-version>
-                        <specification-version>1.4</specification-version>
+                        <specification-version>1.16.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -52,7 +60,15 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>7.9.0.1</specification-version>
+                        <specification-version>8.14.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.util.lookup</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>8.6.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/src/com/sun/hotspot/igv/controlflow/BlockConnectionWidget.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/src/com/sun/hotspot/igv/controlflow/BlockConnectionWidget.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -26,7 +26,9 @@
 import com.sun.hotspot.igv.data.InputBlockEdge;
 import com.sun.hotspot.igv.layout.Link;
 import com.sun.hotspot.igv.layout.Port;
+import java.awt.BasicStroke;
 import java.awt.Point;
+import java.awt.Stroke;
 import java.util.ArrayList;
 import java.util.List;
 import org.netbeans.api.visual.widget.ConnectionWidget;
@@ -37,12 +39,19 @@
  */
 public class BlockConnectionWidget extends ConnectionWidget implements Link {
 
+    private static final Stroke NORMAL_STROKE = new BasicStroke(1.0f);
+    private static final Stroke BOLD_STROKE = new BasicStroke(2.5f);
+    private static final Stroke DASHED_STROKE = new BasicStroke(1.0f, BasicStroke.CAP_SQUARE, BasicStroke.JOIN_MITER, 10.0f, new float[]{5, 5}, 0);
+    private static final Stroke BOLD_DASHED_STROKE = new BasicStroke(2.5f, BasicStroke.CAP_SQUARE, BasicStroke.JOIN_MITER, 10.0f, new float[]{5, 5}, 0);
+
     private BlockWidget from;
     private BlockWidget to;
     private Port inputSlot;
     private Port outputSlot;
     private List<Point> points;
     private InputBlockEdge edge;
+    private boolean isDashed = false;
+    private boolean isBold = false;
 
     public BlockConnectionWidget(ControlFlowScene scene, InputBlockEdge edge) {
         super(scene);
@@ -67,6 +76,30 @@
         return outputSlot;
     }
 
+    public void setBold(boolean bold) {
+        this.isBold = bold;
+        updateStroke();
+    }
+
+    public void setDashed(boolean dashed) {
+        this.isDashed = dashed;
+        updateStroke();
+    }
+
+    private void updateStroke() {
+        Stroke stroke = NORMAL_STROKE;
+        if (isBold) {
+            if (isDashed) {
+                stroke = BOLD_DASHED_STROKE;
+            } else {
+                stroke = BOLD_STROKE;
+            }
+        } else if (isDashed) {
+            stroke = DASHED_STROKE;
+        }
+        setStroke(stroke);
+    }
+
     public void setControlPoints(List<Point> p) {
         this.points = p;
     }
@@ -80,4 +113,9 @@
     public String toString() {
         return "Connection[ " + from.toString() + " - " + to.toString() + "]";
     }
+
+    @Override
+    public boolean isVIP() {
+        return isBold;
+    }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/src/com/sun/hotspot/igv/controlflow/BlockWidget.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/src/com/sun/hotspot/igv/controlflow/BlockWidget.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -31,6 +31,7 @@
 import java.awt.Dimension;
 import java.awt.Font;
 import java.awt.Point;
+import java.awt.Rectangle;
 import org.netbeans.api.visual.border.BorderFactory;
 import org.netbeans.api.visual.model.ObjectState;
 import org.netbeans.api.visual.widget.LabelWidget;
@@ -41,13 +42,13 @@
  */
 public class BlockWidget extends LabelWidget implements Vertex {
 
-    public static final Dimension SIZE = new Dimension(20, 20);
+    public static final Dimension MIN_SIZE = new Dimension(20, 20);
     private InputBlock block;
     private Port inputSlot;
     private Port outputSlot;
     private Cluster cluster;
     private boolean root;
-    private static final Font font = new Font(Font.SERIF, Font.PLAIN, 12);
+    private static final Font font = new Font(Font.SANS_SERIF, Font.PLAIN, 12);
     private static final Font boldFont = font.deriveFont(Font.BOLD);
     public static final Color NORMAL_FOREGROUND_COLOR = Color.BLACK;
     public static final Color HOVER_FOREGROUND_COLOR = Color.BLUE;
@@ -59,29 +60,24 @@
         this.setLabel(block.getName());
         this.setForeground(NORMAL_FOREGROUND_COLOR);
         this.setBorder(BorderFactory.createLineBorder(1, NORMAL_FOREGROUND_COLOR));
-        this.setMinimumSize(SIZE);
-        this.setMaximumSize(SIZE);
+        this.setMinimumSize(MIN_SIZE);
 
         this.setFont(font);
+        this.setAlignment(Alignment.CENTER);
 
         final BlockWidget widget = this;
         inputSlot = new Port() {
-
             public Point getRelativePosition() {
-                return new Point((int) (SIZE.getWidth() / 2), (int) (SIZE.getHeight() / 2));
+                return new Point((int) (getSize().getWidth() / 2), (int) (getSize().getHeight() / 2));
             }
-
             public Vertex getVertex() {
                 return widget;
             }
         };
-
         outputSlot = new Port() {
-
             public Point getRelativePosition() {
-                return new Point((int) (SIZE.getWidth() / 2), (int) (SIZE.getHeight() / 2));
+                return new Point((int) (getSize().getWidth() / 2), (int) (getSize().getHeight() / 2));
             }
-
             public Vertex getVertex() {
                 return widget;
             }
@@ -101,7 +97,12 @@
     }
 
     public Dimension getSize() {
-        return SIZE;
+        Rectangle bounds = getBounds();
+        if (bounds != null) {
+            return bounds.getSize();
+        } else {
+            return MIN_SIZE;
+        }
     }
 
     public void setPosition(Point p) {
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/src/com/sun/hotspot/igv/controlflow/Bundle.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/src/com/sun/hotspot/igv/controlflow/Bundle.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,4 +1,4 @@
-CTL_ControlFlowAction=Open ControlFlow Window
-CTL_ControlFlowTopComponent=ControlFlow Window
-HINT_ControlFlowTopComponent=This is a ControlFlow window
+CTL_ControlFlowAction=Control Flow
+CTL_ControlFlowTopComponent=Control Flow
+HINT_ControlFlowTopComponent=Shows the blocks of the current graph.
 OpenIDE-Module-Name=ControlFlow
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/src/com/sun/hotspot/igv/controlflow/ControlFlowAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/src/com/sun/hotspot/igv/controlflow/ControlFlowAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/src/com/sun/hotspot/igv/controlflow/ControlFlowScene.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/src/com/sun/hotspot/igv/controlflow/ControlFlowScene.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,17 +23,17 @@
  */
 package com.sun.hotspot.igv.controlflow;
 
+import com.sun.hotspot.igv.data.InputBlockEdge;
 import com.sun.hotspot.igv.data.InputBlock;
-import com.sun.hotspot.igv.data.InputBlockEdge;
 import com.sun.hotspot.igv.data.InputGraph;
 import com.sun.hotspot.igv.data.services.InputGraphProvider;
 import com.sun.hotspot.igv.data.InputNode;
+import com.sun.hotspot.igv.util.LookupHistory;
 import java.awt.Color;
 import java.awt.Point;
 import java.awt.Rectangle;
 import java.util.ArrayList;
 import java.util.HashSet;
-import java.util.HashMap;
 import java.util.Set;
 import javax.swing.BorderFactory;
 import org.netbeans.api.visual.action.ActionFactory;
@@ -44,15 +44,14 @@
 import org.netbeans.api.visual.action.WidgetAction;
 import org.netbeans.api.visual.anchor.AnchorFactory;
 import org.netbeans.api.visual.anchor.AnchorShape;
-import org.netbeans.api.visual.layout.LayoutFactory;
 import org.netbeans.api.visual.router.RouterFactory;
 import org.netbeans.api.visual.widget.LayerWidget;
 import org.netbeans.api.visual.widget.Widget;
 import org.netbeans.api.visual.graph.GraphScene;
 import org.netbeans.api.visual.graph.layout.GraphLayout;
+import org.netbeans.api.visual.layout.LayoutFactory;
 import org.netbeans.api.visual.layout.SceneLayout;
 import org.netbeans.api.visual.widget.ConnectionWidget;
-import org.openide.util.Lookup;
 
 /**
  *
@@ -61,13 +60,12 @@
 public class ControlFlowScene extends GraphScene<InputBlock, InputBlockEdge> implements SelectProvider, MoveProvider, RectangularSelectDecorator, RectangularSelectProvider {
 
     private HashSet<BlockWidget> selection;
-    private HashMap<InputBlock, BlockWidget> blockMap;
     private InputGraph oldGraph;
     private LayerWidget edgeLayer;
     private LayerWidget mainLayer;
     private LayerWidget selectLayer;
     private WidgetAction hoverAction = this.createWidgetHoverAction();
-    private WidgetAction selectAction = ActionFactory.createSelectAction(this);
+    private WidgetAction selectAction = new DoubleClickSelectAction(this);
     private WidgetAction moveAction = ActionFactory.createMoveAction(null, this);
 
     public ControlFlowScene() {
@@ -111,27 +109,21 @@
             addNode(b);
         }
 
-        for (InputBlock b : g.getBlocks()) {
-            for (InputBlockEdge e : b.getOutputs()) {
-                addEdge(e);
-                assert g.getBlocks().contains(e.getFrom());
-                assert g.getBlocks().contains(e.getTo());
-                this.setEdgeSource(e, e.getFrom());
-                this.setEdgeTarget(e, e.getTo());
-            }
+        for (InputBlockEdge e : g.getBlockEdges()) {
+            addEdge(e);
+            assert g.getBlocks().contains(e.getFrom());
+            assert g.getBlocks().contains(e.getTo());
+            this.setEdgeSource(e, e.getFrom());
+            this.setEdgeTarget(e, e.getTo());
         }
 
-        GraphLayout layout = new HierarchicalGraphLayout();//GridGraphLayout();
+        GraphLayout<InputBlock, InputBlockEdge> layout = new HierarchicalGraphLayout<InputBlock, InputBlockEdge>();//GridGraphLayout();
         SceneLayout sceneLayout = LayoutFactory.createSceneGraphLayout(this, layout);
         sceneLayout.invokeLayout();
 
         this.validate();
     }
 
-    public BlockWidget getBlockWidget(InputBlock b) {
-        return blockMap.get(b);
-    }
-
     public void clearSelection() {
         for (BlockWidget w : selection) {
             w.setState(w.getState().deriveSelected(false));
@@ -141,7 +133,7 @@
     }
 
     public void selectionChanged() {
-        InputGraphProvider p = Lookup.getDefault().lookup(InputGraphProvider.class);
+        InputGraphProvider p = LookupHistory.getLast(InputGraphProvider.class);//)Utilities.actionsGlobalContext().lookup(InputGraphProvider.class);
         if (p != null) {
             Set<InputNode> inputNodes = new HashSet<InputNode>();
             for (BlockWidget w : selection) {
@@ -204,15 +196,19 @@
     }
 
     public void setNewLocation(Widget widget, Point location) {
-        Point originalLocation = getOriginalLocation(widget);
-        int xOffset = location.x - originalLocation.x;
-        int yOffset = location.y - originalLocation.y;
-        for (Widget w : this.selection) {
-            Point p = new Point(w.getPreferredLocation());
-            p.translate(xOffset, yOffset);
-            w.setPreferredLocation(p);
+        if (selection.contains(widget)) {
+            // move entire selection
+            Point originalLocation = getOriginalLocation(widget);
+            int xOffset = location.x - originalLocation.x;
+            int yOffset = location.y - originalLocation.y;
+            for (Widget w : selection) {
+                Point p = new Point(w.getPreferredLocation());
+                p.translate(xOffset, yOffset);
+                w.setPreferredLocation(p);
+            }
+        } else {
+            widget.setPreferredLocation(location);
         }
-
     }
 
     public Widget createSelectionWidget() {
@@ -271,7 +267,15 @@
     }
 
     protected Widget attachEdgeWidget(InputBlockEdge edge) {
-        ConnectionWidget w = new BlockConnectionWidget(this, edge);
+        BlockConnectionWidget w = new BlockConnectionWidget(this, edge);
+        switch (edge.getState()) {
+            case NEW:
+                w.setBold(true);
+                break;
+            case DELETED:
+                w.setDashed(true);
+                break;
+        }
         w.setRouter(RouterFactory.createDirectRouter());
         w.setTargetAnchorShape(AnchorShape.TRIANGLE_FILLED);
         edgeLayer.addChild(w);
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/src/com/sun/hotspot/igv/controlflow/ControlFlowTopComponent.form	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/src/com/sun/hotspot/igv/controlflow/ControlFlowTopComponent.form	Wed Jul 05 20:35:10 2017 +0200
@@ -3,6 +3,8 @@
 <Form version="1.3" maxVersion="1.3" type="org.netbeans.modules.form.forminfo.JPanelFormInfo">
   <AuxValues>
     <AuxValue name="FormSettings_autoResourcing" type="java.lang.Integer" value="0"/>
+    <AuxValue name="FormSettings_autoSetComponentName" type="java.lang.Boolean" value="false"/>
+    <AuxValue name="FormSettings_generateFQN" type="java.lang.Boolean" value="true"/>
     <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="true"/>
     <AuxValue name="FormSettings_i18nAutoMode" type="java.lang.Boolean" value="false"/>
     <AuxValue name="FormSettings_layoutCodeTarget" type="java.lang.Integer" value="2"/>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/src/com/sun/hotspot/igv/controlflow/ControlFlowTopComponent.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/src/com/sun/hotspot/igv/controlflow/ControlFlowTopComponent.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -25,6 +25,7 @@
 
 import com.sun.hotspot.igv.data.InputGraph;
 import com.sun.hotspot.igv.data.services.InputGraphProvider;
+import com.sun.hotspot.igv.util.LookupHistory;
 import java.awt.BorderLayout;
 import java.io.Serializable;
 import javax.swing.JScrollPane;
@@ -63,17 +64,7 @@
         this.add(panel, BorderLayout.CENTER);
     }
 
-    @Override
-    public void requestFocus() {
-        super.requestFocus();
-        scene.getView().requestFocus();
-    }
 
-    @Override
-    public boolean requestFocusInWindow() {
-        super.requestFocusInWindow();
-        return scene.getView().requestFocusInWindow();
-    }
 
     /** This method is called from within the constructor to
      * initialize the form.
@@ -96,6 +87,7 @@
     }// </editor-fold>//GEN-END:initComponents
     // Variables declaration - do not modify//GEN-BEGIN:variables
     // End of variables declaration//GEN-END:variables
+
     /**
      * Gets default instance. Do not use directly: reserved for *.settings files only,
      * i.e. deserialization routines; otherwise you could get a non-deserialized instance.
@@ -131,7 +123,7 @@
 
     @Override
     public void componentOpened() {
-        Lookup.Template tpl = new Lookup.Template(Object.class);
+        Lookup.Template<InputGraphProvider> tpl = new Lookup.Template<InputGraphProvider>(InputGraphProvider.class);
         result = Utilities.actionsGlobalContext().lookup(tpl);
         result.addLookupListener(this);
     }
@@ -143,16 +135,16 @@
     }
 
     public void resultChanged(LookupEvent lookupEvent) {
-
-        final InputGraphProvider p = Lookup.getDefault().lookup(InputGraphProvider.class);
+        final InputGraphProvider p = LookupHistory.getLast(InputGraphProvider.class);//Utilities.actionsGlobalContext().lookup(InputGraphProvider.class);
         if (p != null) {
             SwingUtilities.invokeLater(new Runnable() {
+
                 public void run() {
-            InputGraph g = p.getGraph();
-            if (g != null) {
-                scene.setGraph(g);
-            }
-        }
+                    InputGraph g = p.getGraph();
+                    if (g != null) {
+                        scene.setGraph(g);
+                    }
+                }
             });
         }
     }
@@ -169,8 +161,8 @@
 
     @Override
     public void requestActive() {
-        scene.getView().requestFocusInWindow();
         super.requestActive();
+        scene.getView().requestFocus();
     }
 
     final static class ResolvableHelper implements Serializable {
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/src/com/sun/hotspot/igv/controlflow/DoubleClickSelectAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,61 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+package com.sun.hotspot.igv.controlflow;
+
+import java.awt.Point;
+import java.awt.event.MouseEvent;
+import org.netbeans.api.visual.action.SelectProvider;
+import org.netbeans.api.visual.action.WidgetAction;
+import org.netbeans.api.visual.widget.Widget;
+
+/**
+ * Selection action that acts on double-click only. Does not support aiming.
+ *
+ * @author Peter Hofer
+ */
+public class DoubleClickSelectAction extends WidgetAction.LockedAdapter {
+
+    private final SelectProvider provider;
+
+    public DoubleClickSelectAction(SelectProvider provider) {
+        this.provider = provider;
+    }
+
+    protected boolean isLocked() {
+        return false;
+    }
+
+    @Override
+    public State mousePressed(Widget widget, WidgetMouseEvent event) {
+        if (event.getClickCount() >= 2 && (event.getButton() == MouseEvent.BUTTON1 || event.getButton() == MouseEvent.BUTTON2)) {
+            boolean invert = (event.getModifiersEx() & MouseEvent.CTRL_DOWN_MASK) != 0;
+            Point point = event.getPoint();
+            if (provider.isSelectionAllowed(widget, point, invert)) {
+                provider.select(widget, point, invert);
+                return State.CHAIN_ONLY;
+            }
+        }
+        return State.REJECTED;
+    }
+}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/src/com/sun/hotspot/igv/controlflow/HierarchicalGraphLayout.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/ControlFlow/src/com/sun/hotspot/igv/controlflow/HierarchicalGraphLayout.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -34,7 +34,7 @@
 import java.util.ArrayList;
 import java.util.Collection;
 import java.util.HashMap;
-import java.util.HashSet;
+import java.util.LinkedHashSet;
 import java.util.List;
 import java.util.Map;
 import java.util.Set;
@@ -76,6 +76,10 @@
         public void setControlPoints(List<Point> list) {
         // Do nothing for now
         }
+
+        public boolean isVIP() {
+            return false;
+        }
     }
 
     private class VertexWrapper implements Vertex {
@@ -127,6 +131,7 @@
         }
 
         public int compareTo(Vertex o) {
+            @SuppressWarnings("unchecked")
             VertexWrapper vw = (VertexWrapper) o;
             return node.toString().compareTo(vw.node.toString());
         }
@@ -138,8 +143,8 @@
 
     protected void performGraphLayout(UniversalGraph<N, E> graph) {
 
-        Set<LinkWrapper> links = new HashSet<LinkWrapper>();
-        Set<VertexWrapper> vertices = new HashSet<VertexWrapper>();
+        Set<LinkWrapper> links = new LinkedHashSet<LinkWrapper>();
+        Set<VertexWrapper> vertices = new LinkedHashSet<VertexWrapper>();
         Map<N, VertexWrapper> vertexMap = new HashMap<N, VertexWrapper>();
 
         for (N node : graph.getNodes()) {
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/nbproject/project.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/nbproject/project.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,2 +1,2 @@
-javac.source=1.5
-javac.compilerargs=-Xlint -Xlint:-serial
+javac.source=1.7
+javac.compilerargs=-Xlint -Xlint:-serial
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/nbproject/project.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/nbproject/project.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -1,126 +1,142 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<project xmlns="http://www.netbeans.org/ns/project/1">
-    <type>org.netbeans.modules.apisupport.project</type>
-    <configuration>
-        <data xmlns="http://www.netbeans.org/ns/nb-module-project/3">
-            <code-name-base>com.sun.hotspot.igv.coordinator</code-name-base>
-            <suite-component/>
-            <module-dependencies>
-                <dependency>
-                    <code-name-base>com.sun.hotspot.igv.data</code-name-base>
-                    <build-prerequisite/>
-                    <compile-dependency/>
-                    <run-dependency>
-                        <specification-version>1.0</specification-version>
-                    </run-dependency>
-                </dependency>
-                <dependency>
-                    <code-name-base>com.sun.hotspot.igv.difference</code-name-base>
-                    <build-prerequisite/>
-                    <compile-dependency/>
-                    <run-dependency>
-                        <specification-version>1.0</specification-version>
-                    </run-dependency>
-                </dependency>
-                <dependency>
-                    <code-name-base>com.sun.hotspot.igv.settings</code-name-base>
-                    <build-prerequisite/>
-                    <compile-dependency/>
-                    <run-dependency>
-                        <specification-version>1.0</specification-version>
-                    </run-dependency>
-                </dependency>
-                <dependency>
-                    <code-name-base>com.sun.hotspot.igv.util</code-name-base>
-                    <build-prerequisite/>
-                    <compile-dependency/>
-                    <run-dependency>
-                        <specification-version>1.0</specification-version>
-                    </run-dependency>
-                </dependency>
-                <dependency>
-                    <code-name-base>org.netbeans.api.progress</code-name-base>
-                    <build-prerequisite/>
-                    <compile-dependency/>
-                    <run-dependency>
-                        <release-version>1</release-version>
-                        <specification-version>1.10.0.1</specification-version>
-                    </run-dependency>
-                </dependency>
-                <dependency>
-                    <code-name-base>org.openide.actions</code-name-base>
-                    <build-prerequisite/>
-                    <compile-dependency/>
-                    <run-dependency>
-                        <specification-version>6.6.1.1</specification-version>
-                    </run-dependency>
-                </dependency>
-                <dependency>
-                    <code-name-base>org.openide.awt</code-name-base>
-                    <build-prerequisite/>
-                    <compile-dependency/>
-                    <run-dependency>
-                        <specification-version>6.11.0.1</specification-version>
-                    </run-dependency>
-                </dependency>
-                <dependency>
-                    <code-name-base>org.openide.dialogs</code-name-base>
-                    <build-prerequisite/>
-                    <compile-dependency/>
-                    <run-dependency>
-                        <specification-version>7.5.1</specification-version>
-                    </run-dependency>
-                </dependency>
-                <dependency>
-                    <code-name-base>org.openide.explorer</code-name-base>
-                    <build-prerequisite/>
-                    <compile-dependency/>
-                    <run-dependency>
-                        <specification-version>6.11</specification-version>
-                    </run-dependency>
-                </dependency>
-                <dependency>
-                    <code-name-base>org.openide.filesystems</code-name-base>
-                    <build-prerequisite/>
-                    <compile-dependency/>
-                    <run-dependency>
-                        <specification-version>7.3</specification-version>
-                    </run-dependency>
-                </dependency>
-                <dependency>
-                    <code-name-base>org.openide.loaders</code-name-base>
-                    <build-prerequisite/>
-                    <compile-dependency/>
-                    <run-dependency>
-                        <specification-version>6.7</specification-version>
-                    </run-dependency>
-                </dependency>
-                <dependency>
-                    <code-name-base>org.openide.nodes</code-name-base>
-                    <build-prerequisite/>
-                    <compile-dependency/>
-                    <run-dependency>
-                        <specification-version>7.2.0.1</specification-version>
-                    </run-dependency>
-                </dependency>
-                <dependency>
-                    <code-name-base>org.openide.util</code-name-base>
-                    <build-prerequisite/>
-                    <compile-dependency/>
-                    <run-dependency>
-                        <specification-version>7.9.0.1</specification-version>
-                    </run-dependency>
-                </dependency>
-                <dependency>
-                    <code-name-base>org.openide.windows</code-name-base>
-                    <build-prerequisite/>
-                    <compile-dependency/>
-                    <run-dependency>
-                        <specification-version>6.16</specification-version>
-                    </run-dependency>
-                </dependency>
-            </module-dependencies>
-            <public-packages/>
-        </data>
-    </configuration>
-</project>
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://www.netbeans.org/ns/project/1">
+    <type>org.netbeans.modules.apisupport.project</type>
+    <configuration>
+        <data xmlns="http://www.netbeans.org/ns/nb-module-project/3">
+            <code-name-base>com.sun.hotspot.igv.coordinator</code-name-base>
+            <suite-component/>
+            <module-dependencies>
+                <dependency>
+                    <code-name-base>com.sun.hotspot.igv.connection</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>1.0</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>com.sun.hotspot.igv.data</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>1.0</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>com.sun.hotspot.igv.difference</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>1.0</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>com.sun.hotspot.igv.settings</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>1.0</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>com.sun.hotspot.igv.util</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>1.0</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.netbeans.api.progress</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <release-version>1</release-version>
+                        <specification-version>1.23.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.actions</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>6.21.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.awt</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>7.30.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.dialogs</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>7.18.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.explorer</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>6.34.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.filesystems</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>7.46.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.loaders</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>7.20.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.nodes</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>7.20.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.util</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>8.14.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.util.lookup</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>8.6.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.windows</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>6.39.1</specification-version>
+                    </run-dependency>
+                </dependency>
+            </module-dependencies>
+            <public-packages/>
+        </data>
+    </configuration>
+</project>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/META-INF/services/com.sun.hotspot.igv.data.services.GroupOrganizer	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,2 +0,0 @@
-com.sun.hotspot.igv.coordinator.StandardGroupOrganizer
-com.sun.hotspot.igv.coordinator.GraphCountGroupOrganizer
\ No newline at end of file
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/Bundle.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/Bundle.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,7 +1,6 @@
-
-AdvancedOption_DisplayName_Coordinator=Settings
-AdvancedOption_Tooltip_Coordinator=Visualization Tool Settings
-CTL_OutlineTopComponent=Outline Window
-CTL_SomeAction=test
-HINT_OutlineTopComponent=This is a Outline window
-OpenIDE-Module-Name=Coordinator
+AdvancedOption_DisplayName_Coordinator=Settings
+AdvancedOption_Tooltip_Coordinator=Visualization Tool Settings
+CTL_OutlineTopComponent=Outline
+CTL_SomeAction=test
+HINT_OutlineTopComponent=Displays loaded groups of graphs.
+OpenIDE-Module-Name=Coordinator
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/FolderNode.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/FolderNode.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -24,18 +24,13 @@
 package com.sun.hotspot.igv.coordinator;
 
 import com.sun.hotspot.igv.coordinator.actions.RemoveCookie;
-import com.sun.hotspot.igv.data.ChangedListener;
-import com.sun.hotspot.igv.data.Group;
-import com.sun.hotspot.igv.data.services.GroupOrganizer;
-import com.sun.hotspot.igv.data.InputGraph;
-import com.sun.hotspot.igv.data.Pair;
+import com.sun.hotspot.igv.data.*;
 import java.awt.Image;
-import java.util.ArrayList;
 import java.util.List;
 import org.openide.nodes.AbstractNode;
 import org.openide.nodes.Children;
 import org.openide.nodes.Node;
-import org.openide.util.Utilities;
+import org.openide.util.ImageUtilities;
 import org.openide.util.lookup.AbstractLookup;
 import org.openide.util.lookup.InstanceContent;
 
@@ -45,107 +40,72 @@
  */
 public class FolderNode extends AbstractNode {
 
-    private GroupOrganizer organizer;
     private InstanceContent content;
-    private List<Pair<String, List<Group>>> structure;
-    private List<String> subFolders;
     private FolderChildren children;
 
-    private static class FolderChildren extends Children.Keys implements ChangedListener<Group> {
+    private static class FolderChildren extends Children.Keys<FolderElement> implements ChangedListener {
+
+        private final Folder folder;
 
-        private FolderNode parent;
-        private List<Group> registeredGroups;
-
-        public void setParent(FolderNode parent) {
-            this.parent = parent;
-            this.registeredGroups = new ArrayList<Group>();
+        public FolderChildren(Folder folder) {
+            this.folder = folder;
+            folder.getChangedEvent().addListener(this);
         }
 
         @Override
-        protected Node[] createNodes(Object arg0) {
-
-            for(Group g : registeredGroups) {
-                g.getChangedEvent().removeListener(this);
-            }
-            registeredGroups.clear();
-
-            Pair<String, List<Group>> p = (Pair<String, List<Group>>) arg0;
-            if (p.getLeft().length() == 0) {
-
-                List<Node> curNodes = new ArrayList<Node>();
-                for (Group g : p.getRight()) {
-                    for (InputGraph graph : g.getGraphs()) {
-                        curNodes.add(new GraphNode(graph));
-                    }
-                    g.getChangedEvent().addListener(this);
-                    registeredGroups.add(g);
-                }
-
-                Node[] result = new Node[curNodes.size()];
-                for (int i = 0; i < curNodes.size(); i++) {
-                    result[i] = curNodes.get(i);
-                }
-                return result;
-
-            } else {
-                return new Node[]{new FolderNode(p.getLeft(), parent.organizer, parent.subFolders, p.getRight())};
+        protected Node[] createNodes(FolderElement e) {
+             if (e instanceof InputGraph) {
+                return new Node[]{new GraphNode((InputGraph) e)};
+            } else if (e instanceof Folder) {
+                 return new Node[]{new FolderNode((Folder) e)};
+             } else {
+                return null;
             }
         }
 
         @Override
         public void addNotify() {
-            this.setKeys(parent.structure);
+            this.setKeys(folder.getElements());
         }
 
-        public void changed(Group source) {
-            List<Pair<String, List<Group>>> newStructure = new ArrayList<Pair<String, List<Group>>>();
-            for(Pair<String, List<Group>> p : parent.structure) {
-                refreshKey(p);
-            }
-        }
-    }
-
-    protected InstanceContent getContent() {
-        return content;
+        @Override
+        public void changed(Object source) {
+            addNotify();
+         }
     }
 
     @Override
     public Image getIcon(int i) {
-        return Utilities.loadImage("com/sun/hotspot/igv/coordinator/images/folder.gif");
+        return ImageUtilities.loadImage("com/sun/hotspot/igv/coordinator/images/folder.png");
     }
 
-    protected FolderNode(String name, GroupOrganizer organizer, List<String> subFolders, List<Group> groups) {
-        this(name, organizer, subFolders, groups, new FolderChildren(), new InstanceContent());
+    protected FolderNode(Folder folder) {
+        this(folder, new FolderChildren(folder), new InstanceContent());
     }
 
-    private FolderNode(String name, GroupOrganizer organizer, List<String> oldSubFolders, final List<Group> groups, FolderChildren children, InstanceContent content) {
+    private FolderNode(final Folder folder, FolderChildren children, InstanceContent content) {
         super(children, new AbstractLookup(content));
-        children.setParent(this);
         this.content = content;
         this.children = children;
-        content.add(new RemoveCookie() {
-
-            public void remove() {
-                for (Group g : groups) {
-                    if (g.getDocument() != null) {
-                        g.getDocument().removeGroup(g);
-                    }
+        if (folder instanceof FolderElement) {
+            final FolderElement folderElement = (FolderElement) folder;
+            this.setDisplayName(folderElement.getName());
+            content.add(new RemoveCookie() {
+                @Override
+                public void remove() {
+                    folderElement.getParent().removeElement(folderElement);
                 }
-            }
-        });
-        init(name, organizer, oldSubFolders, groups);
+            });
+        }
     }
 
-    public void init(String name, GroupOrganizer organizer, List<String> oldSubFolders, List<Group> groups) {
+    public void init(String name, List<Group> groups) {
         this.setDisplayName(name);
-        this.organizer = organizer;
-        this.subFolders = new ArrayList<String>(oldSubFolders);
-        if (name.length() > 0) {
-            this.subFolders.add(name);
+        children.addNotify();
+
+        for (Group g : groups) {
+            content.add(g);
         }
-        structure = organizer.organize(subFolders, groups);
-        assert structure != null;
-        children.addNotify();
     }
 
     @Override
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/GraphCountGroupOrganizer.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,81 +0,0 @@
-/*
- * Copyright (c) 1998, 2007, Oracle and/or its affiliates. All rights reserved.
- * 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 com.sun.hotspot.igv.coordinator;
-
-import com.sun.hotspot.igv.data.Group;
-import com.sun.hotspot.igv.data.Pair;
-import com.sun.hotspot.igv.data.services.GroupOrganizer;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-import java.util.SortedSet;
-import java.util.TreeSet;
-
-/**
- *
- * @author Thomas Wuerthinger
- */
-public class GraphCountGroupOrganizer implements GroupOrganizer {
-
-    public String getName() {
-        return "Graph count structure";
-    }
-
-    public List<Pair<String, List<Group>>> organize(List<String> subFolders, List<Group> groups) {
-
-        List<Pair<String, List<Group>>> result = new ArrayList<Pair<String, List<Group>>>();
-
-        if (subFolders.size() == 0) {
-            Map<Integer, List<Group>> map = new HashMap<Integer, List<Group>>();
-            for (Group g : groups) {
-                Integer cur = g.getGraphs().size();
-                if (!map.containsKey(cur)) {
-                    map.put(cur, new ArrayList<Group>());
-                }
-                map.get(cur).add(g);
-            }
-
-            SortedSet<Integer> keys = new TreeSet<Integer>(map.keySet());
-            for (Integer i : keys) {
-                result.add(new Pair<String, List<Group>>("Graph count " + i, map.get(i)));
-            }
-
-        } else if (subFolders.size() == 1) {
-            for (Group g : groups) {
-                List<Group> children = new ArrayList<Group>();
-                children.add(g);
-                Pair<String, List<Group>> p = new Pair<String, List<Group>>();
-                p.setLeft(g.getName());
-                p.setRight(children);
-                result.add(p);
-            }
-        } else if (subFolders.size() == 2) {
-            result.add(new Pair<String, List<Group>>("", groups));
-        }
-
-        return result;
-    }
-}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/GraphNode.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/GraphNode.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,23 +23,27 @@
  */
 package com.sun.hotspot.igv.coordinator;
 
+import com.sun.hotspot.igv.coordinator.actions.CloneGraphAction;
 import com.sun.hotspot.igv.coordinator.actions.DiffGraphAction;
 import com.sun.hotspot.igv.coordinator.actions.DiffGraphCookie;
-import com.sun.hotspot.igv.coordinator.actions.RemoveCookie;
+import com.sun.hotspot.igv.coordinator.actions.GraphCloneCookie;
+import com.sun.hotspot.igv.coordinator.actions.GraphOpenCookie;
+import com.sun.hotspot.igv.coordinator.actions.GraphRemoveCookie;
 import com.sun.hotspot.igv.data.InputGraph;
+import com.sun.hotspot.igv.data.Properties;
 import com.sun.hotspot.igv.data.services.GraphViewer;
-import com.sun.hotspot.igv.data.services.InputGraphProvider;
 import com.sun.hotspot.igv.util.PropertiesSheet;
 import java.awt.Image;
 import javax.swing.Action;
 import org.openide.actions.OpenAction;
-import org.openide.cookies.OpenCookie;
 import org.openide.nodes.AbstractNode;
 import org.openide.nodes.Children;
-import org.openide.nodes.Node;
+import org.openide.nodes.NodeAdapter;
+import org.openide.nodes.NodeEvent;
+import org.openide.nodes.NodeMemberEvent;
 import org.openide.nodes.Sheet;
+import org.openide.util.ImageUtilities;
 import org.openide.util.Lookup;
-import org.openide.util.Utilities;
 import org.openide.util.lookup.AbstractLookup;
 import org.openide.util.lookup.InstanceContent;
 
@@ -48,7 +52,6 @@
  * @author Thomas Wuerthinger
  */
 public class GraphNode extends AbstractNode {
-
     private InputGraph graph;
 
     /** Creates a new instance of GraphNode */
@@ -56,7 +59,7 @@
         this(graph, new InstanceContent());
     }
 
-    private GraphNode(final InputGraph graph, InstanceContent content) {
+    private GraphNode(InputGraph graph, InstanceContent content) {
         super(Children.LEAF, new AbstractLookup(content));
         this.graph = graph;
         this.setDisplayName(graph.getName());
@@ -66,19 +69,22 @@
 
         if (viewer != null) {
             // Action for opening the graph
-            content.add(new OpenCookie() {
-
-                public void open() {
-                    viewer.view(graph);
-                }
-            });
+            content.add(new GraphOpenCookie(viewer, graph));
         }
 
         // Action for removing a graph
-        content.add(new RemoveCookie() {
+        content.add(new GraphRemoveCookie(graph));
+
+        // Action for diffing to the current graph
+        content.add(new DiffGraphCookie(graph));
 
-            public void remove() {
-                graph.getGroup().removeGraph(graph);
+        // Action for cloning to the current graph
+        content.add(new GraphCloneCookie(viewer, graph));
+
+        this.addNodeListener(new NodeAdapter() {
+            @Override
+            public void childrenRemoved(NodeMemberEvent ev) {
+                GraphNode.this.graph = null;
             }
         });
     }
@@ -86,13 +92,17 @@
     @Override
     protected Sheet createSheet() {
         Sheet s = super.createSheet();
-        PropertiesSheet.initializeSheet(graph.getProperties(), s);
+        Properties p = new Properties();
+        p.add(graph.getProperties());
+        p.setProperty("nodeCount", Integer.toString(graph.getNodes().size()));
+        p.setProperty("edgeCount", Integer.toString(graph.getEdges().size()));
+        PropertiesSheet.initializeSheet(p, s);
         return s;
     }
 
     @Override
     public Image getIcon(int i) {
-        return Utilities.loadImage("com/sun/hotspot/igv/coordinator/images/graph.gif");
+        return ImageUtilities.loadImage("com/sun/hotspot/igv/coordinator/images/graph.png");
     }
 
     @Override
@@ -101,30 +111,28 @@
     }
 
     @Override
-    public <T extends Node.Cookie> T getCookie(Class<T> aClass) {
-        if (aClass == DiffGraphCookie.class) {
-            InputGraphProvider graphProvider = Utilities.actionsGlobalContext().lookup(InputGraphProvider.class);
-
-            InputGraph graphA = null;
-            if (graphProvider != null) {
-                graphA = graphProvider.getGraph();
-            }
-
-            if (graphA != null && !graphA.isDifferenceGraph()) {
-                return (T) new DiffGraphCookie(graphA, graph);
-            }
-        }
-
-        return super.getCookie(aClass);
-    }
-
-    @Override
     public Action[] getActions(boolean b) {
-        return new Action[]{(Action) DiffGraphAction.findObject(DiffGraphAction.class, true), (Action) OpenAction.findObject(OpenAction.class, true)};
+        return new Action[]{(Action) DiffGraphAction.findObject(DiffGraphAction.class, true), (Action) CloneGraphAction.findObject(CloneGraphAction.class, true), (Action) OpenAction.findObject(OpenAction.class, true)};
     }
 
     @Override
     public Action getPreferredAction() {
         return (Action) OpenAction.findObject(OpenAction.class, true);
     }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj) {
+            return true;
+        }
+        if (obj instanceof GraphNode) {
+            return (graph == ((GraphNode) obj).graph);
+        }
+        return false;
+    }
+
+    @Override
+    public int hashCode() {
+        return graph.hashCode();
+    }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/OutlineTopComponent.form	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/OutlineTopComponent.form	Wed Jul 05 20:35:10 2017 +0200
@@ -3,6 +3,8 @@
 <Form version="1.2" maxVersion="1.2" type="org.netbeans.modules.form.forminfo.JPanelFormInfo">
   <AuxValues>
     <AuxValue name="FormSettings_autoResourcing" type="java.lang.Integer" value="0"/>
+    <AuxValue name="FormSettings_autoSetComponentName" type="java.lang.Boolean" value="false"/>
+    <AuxValue name="FormSettings_generateFQN" type="java.lang.Boolean" value="true"/>
     <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="true"/>
     <AuxValue name="FormSettings_i18nAutoMode" type="java.lang.Boolean" value="false"/>
     <AuxValue name="FormSettings_layoutCodeTarget" type="java.lang.Integer" value="2"/>
@@ -14,28 +16,17 @@
 
   <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/>
   <SubComponents>
-    <Container class="javax.swing.JPanel" name="jPanel2">
+    <Container class="javax.swing.JScrollPane" name="treeView">
+      <AuxValues>
+        <AuxValue name="JavaCodeGenerator_CreateCodeCustom" type="java.lang.String" value="new BeanTreeView();"/>
+      </AuxValues>
       <Constraints>
         <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription">
           <BorderConstraints direction="Center"/>
         </Constraint>
       </Constraints>
 
-      <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/>
-      <SubComponents>
-        <Container class="javax.swing.JScrollPane" name="jScrollPane1">
-          <AuxValues>
-            <AuxValue name="JavaCodeGenerator_CreateCodeCustom" type="java.lang.String" value="new BeanTreeView();"/>
-          </AuxValues>
-          <Constraints>
-            <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription">
-              <BorderConstraints direction="Center"/>
-            </Constraint>
-          </Constraints>
-
-          <Layout class="org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout"/>
-        </Container>
-      </SubComponents>
+      <Layout class="org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout"/>
     </Container>
   </SubComponents>
 </Form>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/OutlineTopComponent.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/OutlineTopComponent.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,37 +23,25 @@
  */
 package com.sun.hotspot.igv.coordinator;
 
-import com.sun.hotspot.igv.coordinator.actions.ImportAction;
-import com.sun.hotspot.igv.coordinator.actions.RemoveAction;
-import com.sun.hotspot.igv.coordinator.actions.RemoveAllAction;
-import com.sun.hotspot.igv.coordinator.actions.SaveAllAction;
-import com.sun.hotspot.igv.coordinator.actions.SaveAsAction;
-import com.sun.hotspot.igv.coordinator.actions.StructuredViewAction;
+import com.sun.hotspot.igv.connection.Server;
+import com.sun.hotspot.igv.coordinator.actions.*;
 import com.sun.hotspot.igv.data.GraphDocument;
-import com.sun.hotspot.igv.data.ChangedListener;
 import com.sun.hotspot.igv.data.Group;
 import com.sun.hotspot.igv.data.services.GroupCallback;
-import com.sun.hotspot.igv.data.services.GroupOrganizer;
-import com.sun.hotspot.igv.data.services.GroupReceiver;
 import java.awt.BorderLayout;
-import java.awt.Component;
 import java.io.IOException;
 import java.io.ObjectInput;
 import java.io.ObjectOutput;
 import java.io.Serializable;
-import java.util.ArrayList;
-import java.util.Collection;
-import javax.swing.BoxLayout;
-import javax.swing.JPanel;
 import javax.swing.UIManager;
 import javax.swing.border.Border;
 import org.openide.ErrorManager;
+import org.openide.actions.GarbageCollectAction;
 import org.openide.awt.Toolbar;
 import org.openide.awt.ToolbarPool;
 import org.openide.explorer.ExplorerManager;
 import org.openide.explorer.ExplorerUtils;
 import org.openide.explorer.view.BeanTreeView;
-import org.openide.util.Lookup;
 import org.openide.util.LookupEvent;
 import org.openide.util.LookupListener;
 import org.openide.util.NbBundle;
@@ -72,7 +60,8 @@
     private ExplorerManager manager;
     private GraphDocument document;
     private FolderNode root;
-    private GroupOrganizer organizer;
+    private Server server;
+    private Server binaryServer;
 
     private OutlineTopComponent() {
         initComponents();
@@ -88,17 +77,9 @@
 
     private void initListView() {
         manager = new ExplorerManager();
-        organizer = new StandardGroupOrganizer();
-        root = new FolderNode("", organizer, new ArrayList<String>(), document.getGroups());
+        root = new FolderNode(document);
         manager.setRootContext(root);
-        ((BeanTreeView) this.jScrollPane1).setRootVisible(false);
-
-        document.getChangedEvent().addListener(new ChangedListener<GraphDocument>() {
-
-            public void changed(GraphDocument document) {
-                updateStructure();
-            }
-        });
+        ((BeanTreeView) this.treeView).setRootVisible(false);
 
         associateLookup(ExplorerUtils.createLookup(manager, getActionMap()));
     }
@@ -111,61 +92,41 @@
         this.add(toolbar, BorderLayout.NORTH);
 
         toolbar.add(ImportAction.get(ImportAction.class));
-        toolbar.add(((NodeAction) RemoveAction.get(RemoveAction.class)).createContextAwareInstance(this.getLookup()));
-        toolbar.add(RemoveAllAction.get(RemoveAllAction.class));
 
         toolbar.add(((NodeAction) SaveAsAction.get(SaveAsAction.class)).createContextAwareInstance(this.getLookup()));
         toolbar.add(SaveAllAction.get(SaveAllAction.class));
 
-        toolbar.add(StructuredViewAction.get(StructuredViewAction.class).getToolbarPresenter());
+        toolbar.add(((NodeAction) RemoveAction.get(RemoveAction.class)).createContextAwareInstance(this.getLookup()));
+        toolbar.add(RemoveAllAction.get(RemoveAllAction.class));
+
+        toolbar.add(GarbageCollectAction.get(GarbageCollectAction.class).getToolbarPresenter());
 
         for (Toolbar tb : ToolbarPool.getDefault().getToolbars()) {
             tb.setVisible(false);
         }
-
-        initOrganizers();
-    }
-
-    public void setOrganizer(GroupOrganizer organizer) {
-        this.organizer = organizer;
-        updateStructure();
-    }
-
-    private void initOrganizers() {
-
     }
 
     private void initReceivers() {
 
         final GroupCallback callback = new GroupCallback() {
 
+            @Override
             public void started(Group g) {
-                getDocument().addGroup(g);
+                synchronized(OutlineTopComponent.this) {
+                    getDocument().addElement(g);
+                }
             }
         };
 
-        Collection<? extends GroupReceiver> receivers = Lookup.getDefault().lookupAll(GroupReceiver.class);
-        if (receivers.size() > 0) {
-            JPanel panel = new JPanel();
-            panel.setLayout(new BoxLayout(panel, BoxLayout.Y_AXIS));
-
-            for (GroupReceiver r : receivers) {
-                Component c = r.init(callback);
-                panel.add(c);
-            }
-
-            jPanel2.add(panel, BorderLayout.PAGE_START);
-        }
-    }
-
-    private void updateStructure() {
-        root.init("", organizer, new ArrayList<String>(), document.getGroups());
+        server = new Server(getDocument(), callback, false);
+        binaryServer = new Server(getDocument(), callback, true);
     }
 
     public void clear() {
         document.clear();
     }
 
+    @Override
     public ExplorerManager getExplorerManager() {
         return manager;
     }
@@ -221,6 +182,25 @@
         return PREFERRED_ID;
     }
 
+    @Override
+    public void requestActive() {
+        super.requestActive();
+        treeView.requestFocus();
+    }
+
+    @Override
+    public boolean requestFocus(boolean temporary) {
+        treeView.requestFocus();
+        return super.requestFocus(temporary);
+    }
+
+    @Override
+    protected boolean requestFocusInWindow(boolean temporary) {
+        treeView.requestFocus();
+        return super.requestFocusInWindow(temporary);
+    }
+
+    @Override
     public void resultChanged(LookupEvent lookupEvent) {
     }
 
@@ -228,7 +208,7 @@
     public void readExternal(ObjectInput objectInput) throws IOException, ClassNotFoundException {
         // Not called when user starts application for the first time
         super.readExternal(objectInput);
-        ((BeanTreeView) this.jScrollPane1).setRootVisible(false);
+        ((BeanTreeView) this.treeView).setRootVisible(false);
     }
 
     @Override
@@ -253,19 +233,13 @@
     // <editor-fold defaultstate="collapsed" desc="Generated Code">//GEN-BEGIN:initComponents
     private void initComponents() {
 
-        jPanel2 = new javax.swing.JPanel();
-        jScrollPane1 = new BeanTreeView();
+        treeView = new BeanTreeView();
 
         setLayout(new java.awt.BorderLayout());
-
-        jPanel2.setLayout(new java.awt.BorderLayout());
-        jPanel2.add(jScrollPane1, java.awt.BorderLayout.CENTER);
-
-        add(jPanel2, java.awt.BorderLayout.CENTER);
+        add(treeView, java.awt.BorderLayout.CENTER);
     }// </editor-fold>//GEN-END:initComponents
 
     // Variables declaration - do not modify//GEN-BEGIN:variables
-    private javax.swing.JPanel jPanel2;
-    private javax.swing.JScrollPane jScrollPane1;
+    private javax.swing.JScrollPane treeView;
     // End of variables declaration//GEN-END:variables
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/StandardConfiguration.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/StandardConfiguration.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -4,7 +4,7 @@
     <Row>
         <Toolbar name="Edit" position="1" visible="false"/>
         <Toolbar name="File" position="1" visible="false" />
-        <Toolbar name="Memory" position="1" visible="false" />
+        <Toolbar name="Memory" position="1" visible="true" />
     </Row>
     <Row>
         <Toolbar name="WorkspaceSwitcher" />
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/StandardGroupOrganizer.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,62 +0,0 @@
-/*
- * Copyright (c) 1998, 2007, Oracle and/or its affiliates. All rights reserved.
- * 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 com.sun.hotspot.igv.coordinator;
-
-import com.sun.hotspot.igv.data.Group;
-import com.sun.hotspot.igv.data.services.GroupOrganizer;
-import com.sun.hotspot.igv.data.Pair;
-import java.util.ArrayList;
-import java.util.List;
-
-/**
- *
- * @author Thomas Wuerthinger
- */
-public class StandardGroupOrganizer implements GroupOrganizer {
-
-    public String getName() {
-        return "-- None --";
-    }
-
-    public List<Pair<String, List<Group>>> organize(List<String> subFolders, List<Group> groups) {
-
-        List<Pair<String, List<Group>>> result = new ArrayList<Pair<String, List<Group>>>();
-
-        if (groups.size() == 1 && subFolders.size() > 0) {
-            result.add(new Pair<String, List<Group>>("", groups));
-        } else {
-            for (Group g : groups) {
-                List<Group> children = new ArrayList<Group>();
-                children.add(g);
-                Pair<String, List<Group>> p = new Pair<String, List<Group>>();
-                p.setLeft(g.getName());
-                p.setRight(children);
-                result.add(p);
-            }
-        }
-
-        return result;
-    }
-}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/Bundle.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/Bundle.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,18 +1,10 @@
-CTL_EditFilterAction=Edit...
 CTL_ImportAction=Open...
 CTL_OpenGraphAction=View graph
 CTL_DiffGraphAction=Difference to current graph
-CTL_RemoveAction=Remove methods
-CTL_ApplyFilterAction=Apply
-CTL_FilterAction=Open Filter Window
-CTL_AppliedFilterAction=Open AppliedFilter Window
-CTL_OutlineAction=Open Outline Window
-CTL_MoveFilterUpAction=Move upwards
-CTL_MoveFilterDownAction=Move downwards
-CTL_RemoveFilterAction=Remove
-CTL_RemoveFilterSettingsAction=Remove filter setting
-CTL_SaveAsAction=Save selected methods...
-CTL_SaveAllAction=Save all...
-CTL_SaveFilterSettingsAction=Save filter settings...
-CTL_PropertiesAction=Open Properties Window
+CTL_RemoveAction=Remove selected graphs and groups
+CTL_RemoveAllAction=Remove all graphs and groups
+CTL_OutlineAction=Outline
+CTL_SaveAsAction=Save selected groups...
+CTL_SaveAllAction=Save all groups...
+CTL_PropertiesAction=Open Properties Window 
 CTL_NewFilterAction=New filter...
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/CloneGraphAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,89 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+
+package com.sun.hotspot.igv.coordinator.actions;
+
+import org.openide.nodes.Node;
+import org.openide.util.HelpCtx;
+import org.openide.util.actions.CookieAction;
+
+/**
+ *
+ * @author Thomas Wuerthinger
+ */
+public final class CloneGraphAction extends CookieAction {
+
+    @Override
+    protected void performAction(Node[] activatedNodes) {
+        GraphCloneCookie c = activatedNodes[0].getCookie(GraphCloneCookie.class);
+        assert c != null;
+        c.openClone();
+    }
+
+    @Override
+    protected int mode() {
+        return CookieAction.MODE_EXACTLY_ONE;
+    }
+
+    @Override
+    protected boolean enable(Node[] activatedNodes) {
+        boolean b = super.enable(activatedNodes);
+        if (b) {
+            assert activatedNodes.length == 1;
+            GraphCloneCookie c = activatedNodes[0].getCookie(GraphCloneCookie.class);
+            assert c != null;
+            return true;
+        }
+
+        return false;
+    }
+
+    @Override
+    public String getName() {
+        return "Open clone";
+    }
+
+    @Override
+    protected Class<?>[] cookieClasses() {
+        return new Class<?>[]{
+            GraphCloneCookie.class
+        };
+    }
+
+    @Override
+    protected String iconResource() {
+        return "com/sun/hotspot/igv/coordinator/images/graph.png";
+    }
+
+    @Override
+    public HelpCtx getHelpCtx() {
+        return HelpCtx.DEFAULT_HELP;
+    }
+
+    @Override
+    protected boolean asynchronous() {
+        return false;
+    }
+}
+
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/DiffGraphAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/DiffGraphAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -35,30 +35,49 @@
  */
 public final class DiffGraphAction extends CookieAction {
 
+    @Override
     protected void performAction(Node[] activatedNodes) {
         DiffGraphCookie c = activatedNodes[0].getCookie(DiffGraphCookie.class);
+        assert c != null;
         c.openDiff();
     }
 
+    @Override
     protected int mode() {
         return CookieAction.MODE_EXACTLY_ONE;
     }
 
+    @Override
+    protected boolean enable(Node[] activatedNodes) {
+        boolean b = super.enable(activatedNodes);
+        if (b) {
+            assert activatedNodes.length == 1;
+            DiffGraphCookie c = activatedNodes[0].getCookie(DiffGraphCookie.class);
+            assert c != null;
+            return c.isPossible();
+        }
+
+        return false;
+    }
+
+    @Override
     public String getName() {
         return NbBundle.getMessage(DiffGraphAction.class, "CTL_DiffGraphAction");
     }
 
-    protected Class[] cookieClasses() {
-        return new Class[]{
+    @Override
+    protected Class<?>[] cookieClasses() {
+        return new Class<?>[]{
             DiffGraphCookie.class
         };
     }
 
     @Override
     protected String iconResource() {
-        return "com/sun/hotspot/igv/coordinator/images/diff.gif";
+        return "com/sun/hotspot/igv/coordinator/images/diff.png";
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
@@ -68,3 +87,4 @@
         return false;
     }
 }
+
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/DiffGraphCookie.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/DiffGraphCookie.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -21,12 +21,13 @@
  * questions.
  *
  */
-
 package com.sun.hotspot.igv.coordinator.actions;
 
 import com.sun.hotspot.igv.data.InputGraph;
 import com.sun.hotspot.igv.data.services.GraphViewer;
+import com.sun.hotspot.igv.data.services.InputGraphProvider;
 import com.sun.hotspot.igv.difference.Difference;
+import com.sun.hotspot.igv.util.LookupHistory;
 import org.openide.nodes.Node;
 import org.openide.util.Lookup;
 
@@ -36,21 +37,30 @@
  */
 public class DiffGraphCookie implements Node.Cookie {
 
-    private InputGraph a;
-    private InputGraph b;
+    private InputGraph graph;
+
+    public DiffGraphCookie(InputGraph graph) {
+        this.graph = graph;
+    }
 
-    public DiffGraphCookie(InputGraph a, InputGraph b) {
-        this.a = a;
-        this.b = b;
+    private InputGraph getCurrentGraph() {
+        InputGraphProvider graphProvider = LookupHistory.getLast(InputGraphProvider.class);
+        if (graphProvider != null) {
+            return graphProvider.getGraph();
+        }
+        return null;
+    }
+
+    public boolean isPossible() {
+        return getCurrentGraph() != null;
     }
 
     public void openDiff() {
-
+        InputGraph other = getCurrentGraph();
         final GraphViewer viewer = Lookup.getDefault().lookup(GraphViewer.class);
-
-        if(viewer != null) {
-            InputGraph diffGraph = Difference.createDiffGraph(a, b);
-            viewer.view(diffGraph);
+        if (viewer != null) {
+            InputGraph diffGraph = Difference.createDiffGraph(other, graph);
+            viewer.view(diffGraph, true);
         }
     }
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/GraphCloneCookie.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,43 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+package com.sun.hotspot.igv.coordinator.actions;
+
+import com.sun.hotspot.igv.data.InputGraph;
+import com.sun.hotspot.igv.data.services.GraphViewer;
+import org.openide.nodes.Node;
+
+public class GraphCloneCookie implements Node.Cookie {
+
+    private final GraphViewer viewer;
+    private final InputGraph graph;
+
+    public GraphCloneCookie(GraphViewer viewer, InputGraph graph) {
+        this.viewer = viewer;
+        this.graph = graph;
+    }
+
+    public void openClone() {
+        viewer.view(graph, true);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/GraphOpenCookie.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,44 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+package com.sun.hotspot.igv.coordinator.actions;
+
+import com.sun.hotspot.igv.data.InputGraph;
+import com.sun.hotspot.igv.data.services.GraphViewer;
+import org.openide.cookies.OpenCookie;
+
+public class GraphOpenCookie implements OpenCookie {
+
+    private final GraphViewer viewer;
+    private final InputGraph graph;
+
+    public GraphOpenCookie(GraphViewer viewer, InputGraph graph) {
+        this.viewer = viewer;
+        this.graph = graph;
+    }
+
+    @Override
+    public void open() {
+        viewer.view(graph, false);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/GraphRemoveCookie.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,39 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+package com.sun.hotspot.igv.coordinator.actions;
+
+import com.sun.hotspot.igv.data.InputGraph;
+
+public class GraphRemoveCookie implements RemoveCookie {
+    private final InputGraph graph;
+
+    public GraphRemoveCookie(InputGraph graph) {
+        this.graph = graph;
+    }
+
+    @Override
+    public void remove() {
+        graph.getGroup().removeElement(graph);
+    }
+}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/ImportAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/ImportAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -26,51 +26,54 @@
 
 import com.sun.hotspot.igv.coordinator.OutlineTopComponent;
 import com.sun.hotspot.igv.data.GraphDocument;
+import com.sun.hotspot.igv.data.serialization.BinaryParser;
+import com.sun.hotspot.igv.data.serialization.GraphParser;
+import com.sun.hotspot.igv.data.serialization.ParseMonitor;
 import com.sun.hotspot.igv.data.serialization.Parser;
 import com.sun.hotspot.igv.settings.Settings;
-import com.sun.hotspot.igv.data.serialization.XMLParser;
 import java.awt.event.InputEvent;
 import java.awt.event.KeyEvent;
 import java.io.File;
-import java.io.FileInputStream;
 import java.io.FileNotFoundException;
 import java.io.IOException;
+import java.nio.channels.FileChannel;
+import java.nio.file.StandardOpenOption;
 import javax.swing.Action;
 import javax.swing.JFileChooser;
 import javax.swing.KeyStroke;
+import javax.swing.SwingUtilities;
 import javax.swing.filechooser.FileFilter;
 import org.netbeans.api.progress.ProgressHandle;
 import org.netbeans.api.progress.ProgressHandleFactory;
-import org.openide.DialogDisplayer;
-import org.openide.NotifyDescriptor;
+import org.openide.util.Exceptions;
 import org.openide.util.HelpCtx;
 import org.openide.util.NbBundle;
 import org.openide.util.RequestProcessor;
 import org.openide.util.actions.CallableSystemAction;
-import org.openide.xml.XMLUtil;
-import org.xml.sax.InputSource;
-import org.xml.sax.SAXException;
-import org.xml.sax.XMLReader;
 
 /**
  *
  * @author Thomas Wuerthinger
  */
 public final class ImportAction extends CallableSystemAction {
+    private static final int WORKUNITS = 10000;
 
     public static FileFilter getFileFilter() {
         return new FileFilter() {
 
+            @Override
             public boolean accept(File f) {
-                return f.getName().toLowerCase().endsWith(".xml") || f.isDirectory();
+                return f.getName().toLowerCase().endsWith(".xml") || f.getName().toLowerCase().endsWith(".bgv") || f.isDirectory();
             }
 
+            @Override
             public String getDescription() {
-                return "XML files (*.xml)";
+                return "Graph files (*.xml, *.bgv)";
             }
         };
     }
 
+    @Override
     public void performAction() {
 
         JFileChooser fc = new JFileChooser();
@@ -86,84 +89,79 @@
             }
 
             Settings.get().put(Settings.DIRECTORY, dir.getAbsolutePath());
-
             try {
-                final XMLReader reader = XMLUtil.createXMLReader();
-                final FileInputStream inputStream = new FileInputStream(file);
-                final InputSource is = new InputSource(inputStream);
-
+                final FileChannel channel = FileChannel.open(file.toPath(), StandardOpenOption.READ);
                 final ProgressHandle handle = ProgressHandleFactory.createHandle("Opening file " + file.getName());
-                final int basis = 1000;
-                handle.start(basis);
-                final int start = inputStream.available();
-
-                final XMLParser.ParseMonitor parseMonitor = new XMLParser.ParseMonitor() {
-
-                    public void setProgress(double d) {
+                handle.start(WORKUNITS);
+                final long start = channel.size();
+                ParseMonitor monitor = new ParseMonitor() {
+                    @Override
+                    public void updateProgress() {
                         try {
-                            int curAvailable = inputStream.available();
-                            int prog = (int) (basis * (double) (start - curAvailable) / (double) start);
+                            int prog = (int) (WORKUNITS * (double) channel.position() / (double) start);
                             handle.progress(prog);
                         } catch (IOException ex) {
                         }
                     }
-
+                    @Override
                     public void setState(String state) {
-                        setProgress(0.0);
+                        updateProgress();
                         handle.progress(state);
                     }
                 };
-                final Parser parser = new Parser();
+                final GraphParser parser;
                 final OutlineTopComponent component = OutlineTopComponent.findInstance();
-
-                component.requestActive();
-
+                if (file.getName().endsWith(".xml")) {
+                    parser = new Parser(channel, monitor, null);
+                } else if (file.getName().endsWith(".bgv")) {
+                    parser = new BinaryParser(channel, monitor, component.getDocument(), null);
+                } else {
+                    parser = null;
+                }
                 RequestProcessor.getDefault().post(new Runnable() {
-
+                    @Override
                     public void run() {
-                        GraphDocument document = null;
                         try {
-                            document = parser.parse(reader, is, parseMonitor);
-                            parseMonitor.setState("Finishing");
-                            component.getDocument().addGraphDocument(document);
-                        } catch (SAXException ex) {
-                            String s = "Exception during parsing the XML file, could not load document!";
-                            if (ex instanceof XMLParser.MissingAttributeException) {
-                                XMLParser.MissingAttributeException e = (XMLParser.MissingAttributeException) ex;
-                                s += "\nMissing attribute \"" + e.getAttributeName() + "\"";
+                            final GraphDocument document = parser.parse();
+                            if (document != null) {
+                                SwingUtilities.invokeLater(new Runnable(){
+                                    @Override
+                                    public void run() {
+                                        component.requestActive();
+                                        component.getDocument().addGraphDocument(document);
+                                    }
+                                });
                             }
-                            ex.printStackTrace();
-                            NotifyDescriptor d = new NotifyDescriptor.Message(s, NotifyDescriptor.ERROR_MESSAGE);
-                            DialogDisplayer.getDefault().notify(d);
+                        } catch (IOException ex) {
+                            Exceptions.printStackTrace(ex);
                         }
                         handle.finish();
                     }
                 });
-
-            } catch (SAXException ex) {
-                ex.printStackTrace();
             } catch (FileNotFoundException ex) {
-                ex.printStackTrace();
+                Exceptions.printStackTrace(ex);
             } catch (IOException ex) {
-                ex.printStackTrace();
+                Exceptions.printStackTrace(ex);
             }
         }
     }
 
+    @Override
     public String getName() {
         return NbBundle.getMessage(ImportAction.class, "CTL_ImportAction");
     }
 
     public ImportAction() {
-        putValue(Action.SHORT_DESCRIPTION, "Open an XML graph document");
+        putValue(Action.SHORT_DESCRIPTION, "Open XML graph document...");
         putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_O, InputEvent.CTRL_MASK));
     }
 
     @Override
     protected String iconResource() {
-        return "com/sun/hotspot/igv/coordinator/images/import.gif";
+        return "com/sun/hotspot/igv/coordinator/images/import.png";
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/OutlineAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/OutlineAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -24,7 +24,7 @@
 
 package com.sun.hotspot.igv.coordinator.actions;
 
-import com.sun.hotspot.igv.coordinator.*;
+import com.sun.hotspot.igv.coordinator.OutlineTopComponent;
 import java.awt.event.ActionEvent;
 import javax.swing.AbstractAction;
 import org.openide.util.NbBundle;
@@ -40,6 +40,7 @@
         super(NbBundle.getMessage(OutlineAction.class, "CTL_OutlineAction"));
     }
 
+    @Override
     public void actionPerformed(ActionEvent evt) {
         TopComponent win = OutlineTopComponent.findInstance();
         win.open();
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/RemoveAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/RemoveAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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,6 +36,7 @@
  */
 public final class RemoveAction extends NodeAction {
 
+    @Override
     protected void performAction(Node[] activatedNodes) {
         for (Node n : activatedNodes) {
             RemoveCookie removeCookie = n.getCookie(RemoveCookie.class);
@@ -46,18 +47,20 @@
     }
 
     public RemoveAction() {
-        putValue(Action.SHORT_DESCRIPTION, "Remove");
+        putValue(Action.SHORT_DESCRIPTION, "Remove selected graphs and groups");
     }
 
+    @Override
     public String getName() {
         return NbBundle.getMessage(RemoveAction.class, "CTL_RemoveAction");
     }
 
     @Override
     protected String iconResource() {
-        return "com/sun/hotspot/igv/coordinator/images/remove.gif";
+        return "com/sun/hotspot/igv/coordinator/images/remove.png";
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
@@ -67,6 +70,7 @@
         return false;
     }
 
+    @Override
     protected boolean enable(Node[] nodes) {
         return nodes.length > 0;
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/RemoveAllAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/RemoveAllAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2007, 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
@@ -40,20 +40,22 @@
 public final class RemoveAllAction extends CallableSystemAction {
 
 
+    @Override
     public String getName() {
-        return NbBundle.getMessage(RemoveAllAction.class, "CTL_ImportAction");
+        return NbBundle.getMessage(RemoveAllAction.class, "CTL_RemoveAllAction");
     }
 
     public RemoveAllAction() {
-        putValue(Action.SHORT_DESCRIPTION, "Remove all methods");
+        putValue(Action.SHORT_DESCRIPTION, "Remove all graphs and groups");
         putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_SHIFT, InputEvent.CTRL_MASK));
     }
 
     @Override
     protected String iconResource() {
-        return "com/sun/hotspot/igv/coordinator/images/removeall.gif";
+        return "com/sun/hotspot/igv/coordinator/images/removeall.png";
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/RemoveCookie.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/RemoveCookie.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2007, 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
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/SaveAllAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/SaveAllAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2007, 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
@@ -39,17 +39,19 @@
  */
 public final class SaveAllAction extends CallableSystemAction {
 
+    @Override
     public void performAction() {
         final OutlineTopComponent component = OutlineTopComponent.findInstance();
         SaveAsAction.save(component.getDocument());
     }
 
+    @Override
     public String getName() {
         return NbBundle.getMessage(SaveAllAction.class, "CTL_SaveAllAction");
     }
 
     public SaveAllAction() {
-        putValue(Action.SHORT_DESCRIPTION, "Save all methods to XML file");
+        putValue(Action.SHORT_DESCRIPTION, "Save all groups to XML file...");
         putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_S, InputEvent.CTRL_MASK));
     }
 
@@ -58,6 +60,7 @@
         return "com/sun/hotspot/igv/coordinator/images/saveall.gif";
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/SaveAsAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/SaveAsAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -28,12 +28,8 @@
 import com.sun.hotspot.igv.data.Group;
 import com.sun.hotspot.igv.data.serialization.Printer;
 import com.sun.hotspot.igv.settings.Settings;
-import java.io.File;
-import java.io.FileNotFoundException;
-import java.io.FileOutputStream;
-import java.io.IOException;
-import java.io.OutputStreamWriter;
-import java.io.Writer;
+import java.io.*;
+import javax.swing.Action;
 import javax.swing.JFileChooser;
 import org.openide.nodes.Node;
 import org.openide.util.HelpCtx;
@@ -47,12 +43,17 @@
  */
 public final class SaveAsAction extends NodeAction {
 
+    public SaveAsAction() {
+        putValue(Action.SHORT_DESCRIPTION, "Save selected groups to XML file...");
+    }
+
+    @Override
     protected void performAction(Node[] activatedNodes) {
 
         GraphDocument doc = new GraphDocument();
         for (Node n : activatedNodes) {
             Group group = n.getLookup().lookup(Group.class);
-            doc.addGroup(group);
+            doc.addElement(group);
         }
 
         save(doc);
@@ -75,10 +76,10 @@
             }
             Settings.get().put(Settings.DIRECTORY, dir.getAbsolutePath());
             try {
-                Writer writer = new OutputStreamWriter(new FileOutputStream(file));
-                Printer p = new Printer();
-                p.export(writer, doc);
-                writer.close();
+                try (Writer writer = new OutputStreamWriter(new FileOutputStream(file))) {
+                    Printer p = new Printer();
+                    p.export(writer, doc);
+                }
             } catch (FileNotFoundException e) {
                 e.printStackTrace();
             } catch (IOException e) {
@@ -92,15 +93,17 @@
         return CookieAction.MODE_SOME;
     }
 
+    @Override
     public String getName() {
         return NbBundle.getMessage(SaveAsAction.class, "CTL_SaveAsAction");
     }
 
     @Override
     protected String iconResource() {
-        return "com/sun/hotspot/igv/coordinator/images/save.gif";
+        return "com/sun/hotspot/igv/coordinator/images/save.png";
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
@@ -110,6 +113,7 @@
         return false;
     }
 
+    @Override
     protected boolean enable(Node[] nodes) {
 
         int cnt = 0;
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/actions/StructuredViewAction.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,180 +0,0 @@
-/*
- * Copyright (c) 1998, 2007, Oracle and/or its affiliates. All rights reserved.
- * 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 com.sun.hotspot.igv.coordinator.actions;
-
-import com.sun.hotspot.igv.coordinator.OutlineTopComponent;
-import com.sun.hotspot.igv.data.services.GroupOrganizer;
-import java.awt.Component;
-import java.awt.Image;
-import java.awt.event.ActionEvent;
-import java.awt.event.ActionListener;
-import java.awt.event.ItemEvent;
-import java.awt.event.ItemListener;
-import java.awt.image.BufferedImage;
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.Collections;
-import java.util.Comparator;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-import javax.swing.Action;
-import javax.swing.ButtonGroup;
-import javax.swing.ImageIcon;
-import javax.swing.JButton;
-import javax.swing.JCheckBoxMenuItem;
-import javax.swing.JMenuItem;
-import javax.swing.JPopupMenu;
-import javax.swing.event.PopupMenuEvent;
-import javax.swing.event.PopupMenuListener;
-import org.openide.awt.DropDownButtonFactory;
-import org.openide.util.HelpCtx;
-import org.openide.util.Lookup;
-import org.openide.util.Utilities;
-import org.openide.util.actions.CallableSystemAction;
-
-public class StructuredViewAction extends CallableSystemAction {
-
-    private static JButton dropDownButton;
-    private static ButtonGroup buttonGroup;
-    private static JPopupMenu popup;
-    private MyMenuItemListener menuItemListener;
-    private Map<JMenuItem, GroupOrganizer> map;
-
-    public StructuredViewAction() {
-
-        putValue(Action.SHORT_DESCRIPTION, "Cluster nodes into blocks");
-    }
-
-    @Override
-    public Component getToolbarPresenter() {
-
-        Image iconImage = Utilities.loadImage("com/sun/hotspot/igv/coordinator/images/structure.gif");
-        ImageIcon icon = new ImageIcon(iconImage);
-
-        popup = new JPopupMenu();
-
-        menuItemListener = new MyMenuItemListener();
-
-        buttonGroup = new ButtonGroup();
-
-        Collection<? extends GroupOrganizer> organizersCollection = Lookup.getDefault().lookupAll(GroupOrganizer.class);
-
-        List<GroupOrganizer> organizers = new ArrayList<GroupOrganizer>(organizersCollection);
-        Collections.sort(organizers, new Comparator<GroupOrganizer>() {
-            public int compare(GroupOrganizer a, GroupOrganizer b) {
-                return a.getName().compareTo(b.getName());
-            }
-        });
-
-        map = new HashMap<JMenuItem, GroupOrganizer>();
-
-        boolean first = true;
-        for(GroupOrganizer organizer : organizers) {
-            JCheckBoxMenuItem item = new JCheckBoxMenuItem(organizer.getName());
-            map.put(item, organizer);
-            item.addActionListener(menuItemListener);
-            buttonGroup.add(item);
-            popup.add(item);
-            if(first) {
-                item.setSelected(true);
-                first = false;
-            }
-        }
-
-        dropDownButton = DropDownButtonFactory.createDropDownButton(
-                new ImageIcon(
-                new BufferedImage(32, 32, BufferedImage.TYPE_BYTE_GRAY)),
-                popup);
-
-        dropDownButton.setIcon(icon);
-
-        dropDownButton.setToolTipText("Insert Layer Registration");
-
-        dropDownButton.addItemListener(new ItemListener() {
-
-            public void itemStateChanged(ItemEvent e) {
-                int state = e.getStateChange();
-                if (state == ItemEvent.SELECTED) {
-                    performAction();
-                }
-            }
-        });
-
-        dropDownButton.addActionListener(new ActionListener() {
-            public void actionPerformed(ActionEvent e) {
-                performAction();
-            }
-        });
-
-        popup.addPopupMenuListener(new PopupMenuListener() {
-
-            public void popupMenuCanceled(PopupMenuEvent e) {
-                dropDownButton.setSelected(false);
-            }
-
-            public void popupMenuWillBecomeInvisible(PopupMenuEvent e) {
-                dropDownButton.setSelected(false);
-            }
-
-            public void popupMenuWillBecomeVisible(PopupMenuEvent e) {
-                dropDownButton.setSelected(true);
-            }
-        });
-
-        return dropDownButton;
-
-    }
-
-    private class MyMenuItemListener implements ActionListener {
-
-        public void actionPerformed(ActionEvent ev) {
-            JMenuItem item = (JMenuItem) ev.getSource();
-            GroupOrganizer organizer = map.get(item);
-            assert organizer != null : "Organizer must exist!";
-            OutlineTopComponent.findInstance().setOrganizer(organizer);
-        }
-    }
-
-
-    @Override
-    public void performAction() {
-        popup.show(dropDownButton, 0, dropDownButton.getHeight());
-    }
-
-    public String getName() {
-        return "Structured View";
-    }
-
-    public HelpCtx getHelpCtx() {
-        return HelpCtx.DEFAULT_HELP;
-    }
-
-    @Override
-    protected boolean asynchronous() {
-        return false;
-    }
-
-}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/customLeftWsmode.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/customLeftWsmode.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -4,12 +4,8 @@
     <kind type="view" />
     <state type="joined" />
     <constraints>
-        <path orientation="horizontal" number="0" weight="0.779245283018868"/>
-        <path orientation="vertical" number="0" weight="0.7511825922421949"/>
-        <path orientation="horizontal" number="0" weight="0.5"/>
-        <path orientation="vertical" number="20" weight="0.7"/>
-        <path orientation="horizontal" number="40" weight="0.55"/>
-        <path orientation="horizontal" number="0" weight="0.2711864406779661"/>
+        <path orientation="horizontal" number="0" weight="0.2"/>
+        <path orientation="vertical" number="0" weight="0.75"/>
     </constraints>
     <bounds x="0" y="0" width="0" height="0" />
     <frame state="0"/>
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/diff.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/diff.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/folder.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/folder.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/graph.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/graph.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/import.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/import.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/remove.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/remove.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/removeall.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/removeall.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/save.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/save.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/saveall.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/structure.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/images/structure.png has changed
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/layer.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Coordinator/src/com/sun/hotspot/igv/coordinator/layer.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -1,110 +1,194 @@
 <?xml version="1.0" encoding="UTF-8"?>
-<!DOCTYPE filesystem PUBLIC "-//NetBeans//DTD Filesystem 1.1//EN" "http://www.netbeans.org/dtds/filesystem-1_1.dtd">
+<!DOCTYPE filesystem PUBLIC "-//NetBeans//DTD Filesystem 1.2//EN" "http://www.netbeans.org/dtds/filesystem-1_2.dtd">
 <filesystem>
-    <attr name="Actions\Edit\com-sun-hotspot-igv-bytecodes-SelectBytecodesAction.instance\position" intvalue="200"/>
-    <attr name="Actions\Edit\org-netbeans-core-ui-sysopen-SystemOpenAction.instance\position" intvalue="100"/>
-    <attr name="Actions\Edit\org-openide-actions-CopyAction.instance\position" intvalue="1300"/>
-    <attr name="Actions\Edit\org-openide-actions-CutAction.instance\position" intvalue="1400"/>
-    <attr name="Actions\Edit\org-openide-actions-DeleteAction.instance\position" intvalue="1500"/>
-    <attr name="Actions\Edit\org-openide-actions-FindAction.instance\position" intvalue="1600"/>
-    <attr name="Actions\Edit\org-openide-actions-GotoAction.instance\position" intvalue="1700"/>
-    <attr name="Actions\Edit\org-openide-actions-PasteAction.instance\position" intvalue="1800"/>
-    <attr name="Actions\Edit\org-openide-actions-RedoAction.instance\position" intvalue="1900"/>
-    <attr name="Actions\Edit\org-openide-actions-ReplaceAction.instance\position" intvalue="2000"/>
-    <attr name="Actions\Edit\org-openide-actions-UndoAction.instance\position" intvalue="2100"/>
-
     <folder name="Actions">
         <folder name="File">
-            <file name="com-sun-hotspot-igv-coordinator-actions-SaveAsAction.instance">
-                <attr name="position" intvalue="700"/>
-            </file>
-            <file name="com-sun-hotspot-igv-coordinator-actions-SaveAllAction.instance">
-                <attr name="position" intvalue="800"/>
-            </file>
-            <file name="com-sun-hotspot-igv-coordinator-actions-ImportAction.instance">
-                <attr name="position" intvalue="1000"/>
-            </file>
+            <file name="com-sun-hotspot-igv-coordinator-actions-SaveAsAction.instance"/>
+            <file name="com-sun-hotspot-igv-coordinator-actions-SaveAllAction.instance"/>
+            <file name="com-sun-hotspot-igv-coordinator-actions-ImportAction.instance"/>
         </folder>
         <folder name="Edit">
-
-            <file name="com-sun-hotspot-igv-coordinator-actions-RemoveAction.instance">
-                <attr name="position" intvalue="1200"/>
-            </file>
+            <file name="com-sun-hotspot-igv-coordinator-actions-RemoveAction.instance"/>
+            <file name="com-sun-hotspot-igv-coordinator-actions-RemoveAllAction.instance"/>
         </folder>
         <folder name="Window">
             <file name="com-sun-hotspot-igv-coordinator-actions-OutlineAction.instance"/>
         </folder>
     </folder>
+    
     <folder name="Menu">
         <folder name="File">
+            <file name="Separator2.instance_hidden"/>
+            <file name="Separator3.instance_hidden"/>
+            <file name="SeparatorOpen.instance_hidden"/>
             <file name="com-sun-hotspot-igv-coordinator-actions-ImportAction.shadow">
                 <attr name="originalFile" stringvalue="Actions/File/com-sun-hotspot-igv-coordinator-actions-ImportAction.instance"/>
                 <attr name="position" intvalue="100"/>
             </file>
-            <file name="MySeparator2.instance">
+            <file name="SeparatorSave.instance">
                 <attr name="instanceClass" stringvalue="javax.swing.JSeparator"/>
-                <attr name="position" intvalue="300"/>
+                <attr name="position" intvalue="150"/>
             </file>
             <file name="com-sun-hotspot-igv-coordinator-actions-SaveAsAction.shadow">
                 <attr name="originalFile" stringvalue="Actions/File/com-sun-hotspot-igv-coordinator-actions-SaveAsAction.instance"/>
-                <attr name="position" intvalue="300"/>
+                <attr name="position" intvalue="200"/>
             </file>
             <file name="com-sun-hotspot-igv-coordinator-actions-SaveAllAction.shadow">
                 <attr name="originalFile" stringvalue="Actions/File/com-sun-hotspot-igv-coordinator-actions-SaveAllAction.instance"/>
-                <attr name="position" intvalue="400"/>
-            </file>
-            <file name="MySeparator3.instance">
-                <attr name="instanceClass" stringvalue="javax.swing.JSeparator"/>
-                <attr name="position" intvalue="500"/>
+                <attr name="position" intvalue="300"/>
             </file>
-
-            <file name="org-netbeans-modules-openfile-OpenFileAction.instance_hidden"/>
-            <file name="org-openide-actions-PageSetupAction.instance_hidden"/>
-            <file name="org-openide-actions-PrintAction.instance_hidden"/>
-            <file name="org-openide-actions-SaveAction.instance_hidden"/>
-            <file name="org-openide-actions-SaveAllAction.instance_hidden"/>
-            <file name="org-openide-actions-SaveAsAction.shadow_hidden"/>
-        </folder>
-        <folder name="Edit">
-            <file name="com-sun-hotspot-igv-coordinator-actions-SaveFilterSettingsAction.shadow">
-                <attr name="originalFile" stringvalue="Actions/Edit/com-sun-hotspot-igv-coordinator-actions-SaveFilterSettingsAction.instance"/>
+            <file name="SeparatorRemove.instance">
+                <attr name="instanceClass" stringvalue="javax.swing.JSeparator"/>
+                <attr name="position" intvalue="350"/>
             </file>
             <file name="com-sun-hotspot-igv-coordinator-actions-RemoveAction.shadow">
                 <attr name="originalFile" stringvalue="Actions/Edit/com-sun-hotspot-igv-coordinator-actions-RemoveAction.instance"/>
+                <attr name="position" intvalue="400" />
             </file>
-            <file name="org-netbeans-core-actions-JumpNextAction.shadow_hidden"/>
-            <file name="org-netbeans-core-actions-JumpPrevAction.shadow_hidden"/>
-            <file name="org-openide-actions-CutAction.instance_hidden"/>
-            <file name="org-openide-actions-CopyAction.instance_hidden"/>
-            <file name="org-openide-actions-PasteAction.instance_hidden"/>
-            <file name="org-openide-actions-DeleteAction.instance_hidden"/>
-            <file name="org-openide-actions-FindAction.instance_hidden"/>
-            <file name="org-openide-actions-ReplaceAction.instance_hidden"/>
-            <file name="org-openide-actions-JumpNextAction.shadow_hidden"/>
-            <file name="org-openide-actions-JumpPrevAction.shadow_hidden"/>
+            <file name="com-sun-hotspot-igv-coordinator-actions-RemoveAllAction.shadow">
+                <attr name="originalFile" stringvalue="Actions/Edit/com-sun-hotspot-igv-coordinator-actions-RemoveAllAction.instance"/>
+                <attr name="position" intvalue="500" />
+            </file>
+            
+            <!-- Hidden menu entries from other modules -->
+            <file name="org-netbeans-modules-editor-ExportHtmlAction.shadow_hidden"/>
+            <file name="org-netbeans-modules-openfile-OpenFileAction.shadow_hidden"/>
+            <file name="org-netbeans-modules-openfile-RecentFileAction.shadow_hidden"/>
+            <file name="org-netbeans-modules-print-action-PageSetupAction.shadow_hidden"/>
+            <file name="org-netbeans-modules-print-action-PrintAction.shadow_hidden"/>
+            <file name="org-netbeans-modules-project-ui-CloseProject.shadow_hidden"/>
+            <file name="org-netbeans-modules-project-ui-CustomizeProject.shadow_hidden"/>
+            <file name="org-netbeans-modules-project-ui-NewFile.shadow_hidden"/>
+            <file name="org-netbeans-modules-project-ui-NewProject.shadow_hidden"/>
+            <file name="org-netbeans-modules-project-ui-OpenProject.shadow_hidden"/>
+            <file name="org-netbeans-modules-project-ui-RecentProjects.shadow_hidden"/>
+            <file name="org-netbeans-modules-project-ui-groups-GroupsMenu.shadow_hidden"/>
+            <file name="org-openide-actions-SaveAction.shadow_hidden"/>
+            <file name="org-openide-actions-SaveAllAction.shadow_hidden"/>
+            <file name="org-openide-actions-SaveAsAction.shadow_hidden"/>
         </folder>
-        <file name="GoTo_hidden"/>
-        <folder name="View">
+        
+        <folder name="Edit">
+            <!-- Hidden menu entries from other modules -->
             <file name="Separator1.instance_hidden"/>
             <file name="Separator2.instance_hidden"/>
-            <file name="org-netbeans-core-actions-HTMLViewAction.instance_hidden"/>
-            <file name="org-netbeans-core-actions-LogAction.instance_hidden"/>
+            <file name="SeparatorAfterFindPrevious.instance_hidden"/>
+            <file name="SeparatorAfterProjectsSearch.instance_hidden"/>
+            <file name="WhereUsedAction.shadow_hidden"/>
+            <file name="org-netbeans-modules-editor-MainMenuAction$FindNextAction.instance_hidden"/>
+            <file name="org-netbeans-modules-editor-MainMenuAction$FindPreviousAction.instance_hidden"/>
+            <file name="org-netbeans-modules-editor-MainMenuAction$FindSelectionAction.instance_hidden"/>
+            <file name="org-netbeans-modules-editor-MainMenuAction$PasteFormattedAction.instance_hidden"/>
+            <file name="org-netbeans-modules-editor-MainMenuAction$SelectAllAction.instance_hidden"/>
+            <file name="org-netbeans-modules-editor-MainMenuAction$SelectIdentifierAction.instance_hidden"/>
+            <file name="org-netbeans-modules-editor-MainMenuAction$StartMacroRecordingAction.instance_hidden"/>
+            <file name="org-netbeans-modules-editor-MainMenuAction$StopMacroRecordingAction.instance_hidden"/>
+            <file name="org-netbeans-modules-search-FindInFilesAction.shadow_hidden"/>
+            <file name="org-netbeans-modules-search-ReplaceInFilesAction.shadow_hidden"/>
+            <file name="org-openide-actions-CopyAction.shadow_hidden"/>
+            <file name="org-openide-actions-CutAction.shadow_hidden"/>
+            <file name="org-openide-actions-DeleteAction.shadow_hidden"/>
+            <file name="org-openide-actions-FindAction.shadow_hidden"/>
+            <file name="org-openide-actions-PasteAction.shadow_hidden"/>
+            <file name="org-openide-actions-ReplaceAction.shadow_hidden"/>
+            <file name="sep-before-reposearch.instance_hidden"/>
+        </folder>
+        
+        <folder name="View">
+            <!-- Hidden menu entries from other modules -->
+            <file name="Separator1.instance_hidden"/>
+            <file name="Separator2.instance_hidden"/>
+            <file name="org-netbeans-core-actions-HTMLViewAction.shadow_hidden"/>
+            <file name="org-netbeans-core-actions-LogAction.shadow_hidden"/>
+            <file name="org-netbeans-core-multiview-EditorsAction.instance_hidden"/>
             <file name="org-netbeans-core-windows-actions-ToolbarsListAction.instance_hidden"/>
+            <file name="org-netbeans-modules-editor-NbCodeFoldingAction.instance_hidden"/>
+            <file name="org-netbeans-modules-project-ui-SyncEditorWithViewsAction.shadow_hidden"/>
+            <file name="org-netbeans-modules-versioning-ShowTextAnnotationsAction.shadow_hidden"/>
+            <file name="org-netbeans-modules-versioning-diff-ShowDiffSidebarAction.shadow_hidden"/>
+            <file name="toggle-line-numbers.shadow_hidden"/>
+            <file name="toggle-non-printable-characters.shadow_hidden"/>
+            <file name="toggle-toolbar.shadow_hidden"/>
         </folder>
+        
+        <!-- Hidden menus -->
+        <folder name="GoTo_hidden"/>
+        <folder name="Source_hidden"/>
+        <folder name="Refactoring_hidden"/>
+        <folder name="BuildProject_hidden"/>
+        <folder name="RunProject_hidden"/>
+        <folder name="Versioning_hidden"/>
+        
+        <folder name="Tools">
+            <!-- Hidden menu entries from other modules -->
+            <file name="LibrariesCustomizerAction.shadow_hidden"/>
+            <file name="PaletteManager_hidden"/>
+            <file name="Separator1.instance_hidden"/>
+            <file name="Separator2.instance_hidden"/>
+            <file name="ServerManagerAction3.shadow_hidden"/>
+            <file name="VariablesCustomizerAction.shadow_hidden"/>
+            <file name="org-netbeans-modules-autoupdate-ui-actions-PluginManagerAction.shadow_hidden"/>
+            <file name="org-netbeans-modules-favorites-templates-TemplatesAction.shadow_hidden"/>
+            <file name="org-netbeans-modules-options-OptionsWindowAction-separatorBefore.instance_hidden"/>
+            <file name="org-netbeans-modules-xml-catalog-CatalogAction.shadow_hidden"/>
+            <file name="org-openide-actions-ToolsAction.shadow_hidden"/>
+        </folder>
+        
         <folder name="Window">
             <file name="OutlineAction.shadow">
                 <attr name="originalFile" stringvalue="Actions/Window/com-sun-hotspot-igv-coordinator-actions-OutlineAction.instance"/>
             </file>
+            
+            <!-- Hidden menu entries from other modules -->
+            <file name="Debug_hidden"/>
+            <file name="Navigator_hidden"/>
+            <file name="Other_hidden"/>
+            <file name="Output_hidden"/>
+            <file name="ProgressListAction.shadow_hidden"/>
+            <file name="ShowPaletteAction.shadow_hidden"/>
+            <file name="SwitchToRecentDocumentAction.shadow_hidden"/>
+            <file name="Versioning_hidden"/>
+            <file name="org-netbeans-core-ide-ServicesTabAction.shadow_hidden"/>
+            <file name="org-netbeans-modules-favorites-View.shadow_hidden"/>
+            <file name="org-netbeans-modules-project-ui-logical-tab-action.shadow_hidden"/>
+            <file name="org-netbeans-modules-project-ui-physical-tab-action.shadow_hidden"/>
+            <file name="org-netbeans-modules-tasklist-ui-TaskListAction.shadow_hidden"/>
+            <file name="CloneDocumentAction.shadow_hidden"/>
+        </folder>
+
+        <folder name="Help">
+            <!-- Hidden menu entries from other modules -->
+            <file name="Separator1.instance_hidden"/>
+            <file name="netbeans-kb.url_hidden"/>
+            <file name="org-netbeans-modules-autoupdate-ui-actions-CheckForUpdatesAction.shadow_hidden"/>
+            <file name="org-netbeans-modules-bugzilla-ReportNBIssueAction.shadow_hidden"/>
+            <file name="org-netbeans-modules-usersguide-master.xml_hidden"/>
+            <file name="shortcuts.xml_hidden"/>
         </folder>
     </folder>
-    <folder name="Toolbars">
-        <file name="Standard.xml" url="StandardConfiguration.xml"/>
+
+    <folder name="OptionsDialog">
+        <!-- Hidden option tabs from other modules -->
+        <file name="Editor.instance_hidden"/>
+        <file name="FontsAndColors.instance_hidden"/>
+        <file name="General.instance_hidden"/>
+        <file name="Keymaps.instance_hidden"/>
+        <folder name="Advanced">
+            <file name="Files.instance_hidden"/>
+            <file name="IssueTracking.instance_hidden"/>
+            <file name="JavaScript.instance_hidden"/>
+            <file name="Spellchecker.instance_hidden"/>
+            <file name="TermAdvancedOption.instance_hidden"/>
+            <file name="ToDo.instance_hidden"/>
+            <file name="Versioning.instance_hidden"/>
+        </folder>
     </folder>
+    
     <folder name="Windows2">
         <folder name="Components">
             <file name="OutlineTopComponent.settings" url="OutlineTopComponentSettings.xml"/>
         </folder>
-        <folder name="Modes">
+        <folder name="Modes">  
             <file name="customLeft.wsmode" url="customLeftWsmode.xml"/>
             <folder name="customLeft">
                 <file name="OutlineTopComponent.wstcref" url="OutlineTopComponentWstcref.xml"/>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/manifest.mf	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/manifest.mf	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
-Manifest-Version: 1.0
-OpenIDE-Module: com.sun.hotspot.igv.data
-OpenIDE-Module-Localizing-Bundle: com/sun/hotspot/igv/data/Bundle.properties
-OpenIDE-Module-Specification-Version: 1.0
-
+Manifest-Version: 1.0
+OpenIDE-Module: com.sun.hotspot.igv.data
+OpenIDE-Module-Localizing-Bundle: com/sun/hotspot/igv/data/Bundle.properties
+OpenIDE-Module-Specification-Version: 1.0
+
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/nbproject/project.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/nbproject/project.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,2 +1,8 @@
-javac.source=1.5
-javac.compilerargs=-Xlint -Xlint:-serial
+javac.source=1.7
+javac.compilerargs=-Xlint -Xlint:-serial
+src.dir=src
+build.test.classes.dir=${build.dir}/test/classes
+build.test.results.dir=${build.dir}/test/results
+test.src.dir=test
+build.test.classes.dir=${build.dir}/test/classes
+build.test.results.dir=${build.dir}/test/results
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/nbproject/project.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/nbproject/project.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -6,6 +6,19 @@
             <code-name-base>com.sun.hotspot.igv.data</code-name-base>
             <suite-component/>
             <module-dependencies/>
+            <test-dependencies>
+                <test-type>
+                    <name>unit</name>
+                    <test-dependency>
+                        <code-name-base>org.netbeans.libs.junit4</code-name-base>
+                        <compile-dependency/>
+                    </test-dependency>
+                    <test-dependency>
+                        <code-name-base>org.openide.util</code-name-base>
+                        <compile-dependency/>
+                    </test-dependency>
+                </test-type>
+            </test-dependencies>
             <public-packages>
                 <package>com.sun.hotspot.igv.data</package>
                 <package>com.sun.hotspot.igv.data.serialization</package>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/ChangedEvent.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/ChangedEvent.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -24,20 +24,22 @@
 package com.sun.hotspot.igv.data;
 
 /**
- *
+ * Class representing a generic changed event.
  * @author Thomas Wuerthinger
+ * @param <T>
  */
 public class ChangedEvent<T> extends Event<ChangedListener<T>> {
 
     private T object;
 
-    public ChangedEvent() {
-    }
-
+    /**
+     * Creates a new event with the specific object as the one for which the event gets fired.
+     */
     public ChangedEvent(T object) {
         this.object = object;
     }
 
+    @Override
     protected void fire(ChangedListener<T> l) {
         l.changed(object);
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/ChangedEventProvider.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/ChangedEventProvider.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2007, 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,10 +25,14 @@
 package com.sun.hotspot.igv.data;
 
 /**
- *
+ * Provides a changed event object.
  * @author Thomas Wuerthinger
+ * @param <T> Class for which the changed event fires.
  */
 public interface ChangedEventProvider<T> {
 
-    public ChangedEvent<T> getChangedEvent();
+    /**
+     * Returns the changed event object. Should always return the same instance.
+     */
+    ChangedEvent<T> getChangedEvent();
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/ChangedListener.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/ChangedListener.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -24,10 +24,15 @@
 package com.sun.hotspot.igv.data;
 
 /**
- *
+ * Listens to changed events.
  * @author Thomas Wuerthinger
+ * @param <T> Class for which the changed event fires.
  */
 public interface ChangedListener<T> {
 
-    public void changed(T source);
+    /**
+     * This method is called everytime a changed event is fired.
+     * @param source Object that has changed.
+     */
+    void changed(T source);
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/ControllableChangedListener.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,56 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+
+package com.sun.hotspot.igv.data;
+
+/**
+ *
+ * @author Thomas Wuerthinger
+ */
+public abstract class ControllableChangedListener<T> implements ChangedListener<T>{
+
+    private boolean enabled;
+
+
+    public ControllableChangedListener() {
+        enabled = true;
+    }
+
+    public boolean isEnabled() {
+        return enabled;
+    }
+
+    public void setEnabled(boolean b) {
+        enabled = b;
+    }
+
+    @Override
+    public void changed(T source) {
+        if(enabled) {
+            filteredChanged(source);
+        }
+    }
+
+    public abstract void filteredChanged(T source);
+}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/Event.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/Event.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -33,23 +33,48 @@
 public abstract class Event<L> {
 
     private List<L> listener;
+    private boolean fireEvents;
+    private boolean eventWasFired;
 
     public Event() {
-        listener = new ArrayList<L>();
+        listener = new ArrayList<>();
+        fireEvents = true;
     }
 
     public void addListener(L l) {
         listener.add(l);
     }
 
-    public void removeListener(L l) {
+    /**
+     * Remove listener
+     * @param l
+     */
+    public void removeListener(final L l) {
         listener.remove(l);
     }
 
     public void fire() {
-        List<L> tmpList = new ArrayList<L>(listener);
-        for (L l : tmpList) {
-            fire(l);
+        if(fireEvents) {
+            List<L> tmpList = new ArrayList<>(listener);
+            for (L l : tmpList) {
+                fire(l);
+            }
+        } else {
+            eventWasFired = true;
+        }
+    }
+
+    public void beginAtomic() {
+        assert fireEvents : "endAtomic has to be called before another beginAtomic may be called";
+        this.fireEvents = false;
+        this.eventWasFired = false;
+    }
+
+    public void endAtomic() {
+        assert !fireEvents : "beginAtomic has to be called first";
+        this.fireEvents = true;
+        if(eventWasFired) {
+            fire();
         }
     }
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/Folder.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,33 @@
+/*
+ * 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.
+ *
+ */
+package com.sun.hotspot.igv.data;
+
+import java.util.List;
+
+public interface Folder {
+    List<? extends FolderElement> getElements();
+    void removeElement(FolderElement element);
+    void addElement(FolderElement group);
+    ChangedEvent<? extends Folder> getChangedEvent();
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/FolderElement.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,31 @@
+/*
+ * 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.
+ *
+ */
+package com.sun.hotspot.igv.data;
+
+public interface FolderElement {
+
+    Folder getParent();
+    String getName();
+    void setParent(Folder parent);
+}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/GraphDocument.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/GraphDocument.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -24,53 +24,36 @@
 package com.sun.hotspot.igv.data;
 
 import java.util.ArrayList;
-import java.util.Collections;
 import java.util.List;
 
 /**
  *
  * @author Thomas Wuerthinger
  */
-public class GraphDocument extends Properties.Entity implements ChangedEventProvider<GraphDocument> {
+public class GraphDocument extends Properties.Entity implements ChangedEventProvider<GraphDocument>, Folder {
 
-    private List<Group> groups;
+    private List<FolderElement> elements;
     private ChangedEvent<GraphDocument> changedEvent;
 
     public GraphDocument() {
-        groups = new ArrayList<Group>();
-        changedEvent = new ChangedEvent<GraphDocument>(this);
+        elements = new ArrayList<>();
+        changedEvent = new ChangedEvent<>(this);
     }
 
     public void clear() {
-        groups.clear();
+        elements.clear();
         getChangedEvent().fire();
     }
 
+    @Override
     public ChangedEvent<GraphDocument> getChangedEvent() {
         return changedEvent;
     }
 
-    public List<Group> getGroups() {
-        return Collections.unmodifiableList(groups);
-    }
-
-    public void addGroup(Group group) {
-        group.setDocument(this);
-        groups.add(group);
-        getChangedEvent().fire();
-    }
-
-    public void removeGroup(Group group) {
-        if (groups.contains(group)) {
-            group.setDocument(null);
-            groups.remove(group);
-            getChangedEvent().fire();
-        }
-    }
-
     public void addGraphDocument(GraphDocument document) {
-        for (Group g : document.groups) {
-            this.addGroup(g);
+        for (FolderElement e : document.elements) {
+            e.setParent(this);
+            this.addElement(e);
         }
         document.clear();
         getChangedEvent().fire();
@@ -80,12 +63,30 @@
     public String toString() {
         StringBuilder sb = new StringBuilder();
 
-        sb.append("GraphDocument: " + getProperties().toString() + " \n\n");
-        for (Group g : getGroups()) {
+        sb.append("GraphDocument: ").append(getProperties().toString()).append(" \n\n");
+        for (FolderElement g : getElements()) {
             sb.append(g.toString());
             sb.append("\n\n");
         }
 
         return sb.toString();
     }
+
+    @Override
+    public List<? extends FolderElement> getElements() {
+        return elements;
+    }
+
+    @Override
+    public void removeElement(FolderElement element) {
+        if (elements.remove(element)) {
+            getChangedEvent().fire();
+        }
+    }
+
+    @Override
+    public void addElement(FolderElement element) {
+        elements.add(element);
+        getChangedEvent().fire();
+    }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/Group.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/Group.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,49 +23,36 @@
  */
 package com.sun.hotspot.igv.data;
 
-import com.sun.hotspot.igv.data.ChangedEvent;
-import com.sun.hotspot.igv.data.ChangedEventProvider;
-import com.sun.hotspot.igv.data.Properties;
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Set;
+import java.util.*;
 
 /**
  *
  * @author Thomas Wuerthinger
  */
-public class Group extends Properties.Entity implements ChangedEventProvider<Group> {
+public class Group extends Properties.Entity implements ChangedEventProvider<Group>, Folder, FolderElement {
 
-    private List<InputGraph> graphs;
+    private final List<FolderElement> elements;
+    private final List<InputGraph> graphs;
+
+    private InputMethod method;
     private transient ChangedEvent<Group> changedEvent;
-    private GraphDocument document;
-    private InputMethod method;
-    private String assembly;
+    private Folder parent;
 
-    public Group() {
-        graphs = new ArrayList<InputGraph>();
-        init();
-    }
+    public Group(Folder parent) {
+        elements = new ArrayList<>();
+        graphs = new ArrayList<>();
+        changedEvent = new ChangedEvent<>(this);
+        this.parent = parent;
 
-    private void init() {
-        changedEvent = new ChangedEvent<Group>(this);
+        // Ensure that name and type are never null
+        getProperties().setProperty("name", "");
+        getProperties().setProperty("type", "");
     }
 
     public void fireChangedEvent() {
         changedEvent.fire();
     }
 
-    public void setAssembly(String s) {
-        this.assembly = s;
-    }
-
-    public String getAssembly() {
-        return assembly;
-    }
-
     public void setMethod(InputMethod method) {
         this.method = method;
     }
@@ -74,68 +61,120 @@
         return method;
     }
 
-    void setDocument(GraphDocument document) {
-        this.document = document;
-    }
-
-    public GraphDocument getDocument() {
-        return document;
-    }
-
+    @Override
     public ChangedEvent<Group> getChangedEvent() {
         return changedEvent;
     }
 
-    public List<InputGraph> getGraphs() {
-        return Collections.unmodifiableList(graphs);
+    @Override
+    public List<FolderElement> getElements() {
+        return Collections.unmodifiableList(elements);
+    }
+
+    public int getGraphsCount() {
+        return elements.size();
     }
 
-    public void addGraph(InputGraph g) {
-        assert g != null;
-        assert !graphs.contains(g);
-        graphs.add(g);
+    @Override
+    public void addElement(FolderElement element) {
+        elements.add(element);
+        if (element instanceof InputGraph) {
+            graphs.add((InputGraph) element);
+        } else {
+
+        }
+        element.setParent(this);
         changedEvent.fire();
     }
 
-    public void removeGraph(InputGraph g) {
-        int index = graphs.indexOf(g);
-        if (index != -1) {
-            graphs.remove(g);
-            changedEvent.fire();
-        }
-    }
-
     public Set<Integer> getAllNodes() {
-        Set<Integer> result = new HashSet<Integer>();
-        for (InputGraph g : graphs) {
-            Set<Integer> ids = g.getNodesAsSet();
-            result.addAll(g.getNodesAsSet());
-            for (Integer i : ids) {
-                result.add(-i);
+        Set<Integer> result = new HashSet<>();
+        for (FolderElement e : elements) {
+            if (e instanceof InputGraph) {
+                InputGraph g = (InputGraph) e;
+                result.addAll(g.getNodesAsSet());
             }
         }
         return result;
     }
 
-    public InputGraph getLastAdded() {
-        if (graphs.size() == 0) {
-            return null;
-        }
-        return graphs.get(graphs.size() - 1);
-    }
-
     @Override
     public String toString() {
         StringBuilder sb = new StringBuilder();
-        sb.append("Group " + getProperties().toString() + "\n");
-        for (InputGraph g : graphs) {
+        sb.append("Group ").append(getProperties()).append("\n");
+        for (FolderElement g : elements) {
             sb.append(g.toString());
-            sb.append("\n");
+            sb.append('\n');
         }
         return sb.toString();
     }
 
+    @Override
     public String getName() {
         return getProperties().get("name");
     }
+
+    public String getType() {
+        return getProperties().get("type");
+
+    }
+
+    InputGraph getPrev(InputGraph graph) {
+        InputGraph lastGraph = null;
+        for (FolderElement e : elements) {
+            if (e == graph) {
+                return lastGraph;
+            }
+            if (e instanceof InputGraph) {
+                lastGraph = (InputGraph) e;
+            }
+        }
+        return null;
+    }
+
+    InputGraph getNext(InputGraph graph) {
+        boolean found = false;
+        for (FolderElement e : elements) {
+            if (e == graph) {
+                found = true;
+            } else if (found && e instanceof InputGraph) {
+                return (InputGraph) e;
+            }
+        }
+        return null;
+    }
+
+    public InputGraph getLastGraph() {
+        InputGraph lastGraph = null;
+        for (FolderElement e : elements) {
+            if (e instanceof InputGraph) {
+                lastGraph = (InputGraph) e;
+            }
+        }
+        return lastGraph;
+    }
+
+    @Override
+    public Folder getParent() {
+         return parent;
+    }
+
+    @Override
+    public void removeElement(FolderElement element) {
+        if (elements.remove(element)) {
+            if (element instanceof InputGraph) {
+                graphs.remove((InputGraph) element);
+            }
+            changedEvent.fire();
+        }
+    }
+
+    public List<InputGraph> getGraphs() {
+        return graphs;
+    }
+
+    @Override
+    public void setParent(Folder parent) {
+        this.parent = parent;
+    }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/InputBlock.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/InputBlock.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,12 +23,7 @@
  */
 package com.sun.hotspot.igv.data;
 
-import java.awt.Rectangle;
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Set;
+import java.util.*;
 
 /**
  *
@@ -37,104 +32,81 @@
 public class InputBlock {
 
     private List<InputNode> nodes;
-    private List<String> successorNames;
     private String name;
     private InputGraph graph;
-    private Rectangle bounds;
     private Set<InputBlock> successors;
-    private Set<InputBlock> predecessors;
-    private Set<InputBlockEdge> inputs;
-    private Set<InputBlockEdge> outputs;
+
+    @Override
+    public int hashCode() {
+        return name.hashCode();
+    }
+
+    @Override
+    public boolean equals(Object o) {
+
+        if (o == this) {
+            return true;
+        }
+
+        if (o == null || (!(o instanceof InputBlock))) {
+            return false;
+        }
 
-    public InputBlock(InputGraph graph, String name) {
+        final InputBlock b = (InputBlock)o;
+        final boolean result = b.nodes.equals(nodes) && b.name.equals(name) && b.successors.size() == successors.size();
+        if (!result) {
+            return false;
+        }
+
+        final HashSet<String> s = new HashSet<>();
+        for (InputBlock succ : successors) {
+            s.add(succ.name);
+        }
+
+        for (InputBlock succ : b.successors) {
+            if (!s.contains(succ.name)) {
+                return false;
+            }
+        }
+
+        return true;
+    }
+
+    InputBlock(InputGraph graph, String name) {
         this.graph = graph;
         this.name = name;
-        nodes = new ArrayList<InputNode>();
-        successorNames = new ArrayList<String>();
-        successors = new HashSet<InputBlock>();
-        predecessors = new HashSet<InputBlock>();
-        inputs = new HashSet<InputBlockEdge>();
-        outputs = new HashSet<InputBlockEdge>();
-    }
-
-    public void removeSuccessor(InputBlock b) {
-        if (successors.contains(b)) {
-            successors.remove(b);
-            b.predecessors.remove(this);
-            InputBlockEdge e = new InputBlockEdge(this, b);
-            assert outputs.contains(e);
-            outputs.remove(e);
-            assert b.inputs.contains(e);
-            b.inputs.remove(e);
-        }
+        nodes = new ArrayList<>();
+        successors = new LinkedHashSet<>(2);
     }
 
     public String getName() {
         return name;
     }
 
-    public void setName(String s) {
-        name = s;
-    }
-
     public List<InputNode> getNodes() {
         return Collections.unmodifiableList(nodes);
     }
 
     public void addNode(int id) {
-        InputNode n = graph.getNode(id);
-        assert n != null;
-        graph.setBlock(n, this);
-        addNode(graph.getNode(id));
-    }
-
-    public void addNode(InputNode node) {
-        assert !nodes.contains(node);
+        InputNode node = graph.getNode(id);
+        assert node != null;
+        assert !nodes.contains(node) : "duplicate : " + node;
+        graph.setBlock(node, this);
         nodes.add(node);
     }
 
-    public Set<InputBlock> getPredecessors() {
-        return Collections.unmodifiableSet(predecessors);
-    }
-
     public Set<InputBlock> getSuccessors() {
         return Collections.unmodifiableSet(successors);
     }
 
-    public Set<InputBlockEdge> getInputs() {
-        return Collections.unmodifiableSet(inputs);
-    }
-
-    public Set<InputBlockEdge> getOutputs() {
-        return Collections.unmodifiableSet(outputs);
-    }
-
-    // resolveBlockLinks must be called afterwards
-    public void addSuccessor(String name) {
-        successorNames.add(name);
+    @Override
+    public String toString() {
+        return "Block " + this.getName();
     }
 
-    public void resolveBlockLinks() {
-        for (String s : successorNames) {
-            InputBlock b = graph.getBlock(s);
-            addSuccessor(b);
-        }
-
-        successorNames.clear();
-    }
-
-    public void addSuccessor(InputBlock b) {
+    void addSuccessor(InputBlock b) {
         if (!successors.contains(b)) {
             successors.add(b);
-            b.predecessors.add(this);
-            InputBlockEdge e = new InputBlockEdge(this, b);
-            outputs.add(e);
-            b.inputs.add(e);
         }
     }
-
-    @Override
-    public String toString() {
-        return this.getName();
-    }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/InputBlockEdge.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/InputBlockEdge.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -29,8 +29,15 @@
  */
 public class InputBlockEdge {
 
+    public enum State {
+        SAME,
+        NEW,
+        DELETED
+    }
+
     private InputBlock from;
     private InputBlock to;
+    private State state = State.SAME;
 
     public InputBlockEdge(InputBlock from, InputBlock to) {
         assert from != null;
@@ -47,13 +54,21 @@
         return to;
     }
 
+    public State getState() {
+        return state;
+    }
+
+    public void setState(State state) {
+        this.state = state;
+    }
+
     @Override
     public boolean equals(Object obj) {
-        if (obj instanceof InputBlockEdge && obj != null) {
+        if (obj != null && obj instanceof InputBlockEdge) {
             InputBlockEdge e = (InputBlockEdge) obj;
             return e.from.equals(from) && e.to.equals(to);
         }
-        return super.equals(obj);
+        return false;
     }
 
     @Override
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/InputBytecode.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/InputBytecode.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -31,11 +31,15 @@
 
     private int bci;
     private String name;
+    private String operands;
+    private String comment;
     private InputMethod inlined;
 
-    public InputBytecode(int bci, String name) {
+    public InputBytecode(int bci, String name, String operands, String comment) {
         this.bci = bci;
         this.name = name;
+        this.operands = operands;
+        this.comment = comment;
     }
 
     public InputMethod getInlined() {
@@ -53,4 +57,12 @@
     public String getName() {
         return name;
     }
+
+    public String getOperands() {
+        return operands;
+    }
+
+    public String getComment() {
+        return comment;
+    }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/InputEdge.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/InputEdge.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,6 +23,10 @@
  */
 package com.sun.hotspot.igv.data;
 
+import java.util.Comparator;
+import java.util.WeakHashMap;
+import java.lang.ref.WeakReference;
+
 /**
  *
  * @author Thomas Wuerthinger
@@ -30,21 +34,83 @@
 public class InputEdge {
 
     public enum State {
-
+        IMMUTABLE,
         SAME,
         NEW,
         DELETED
     }
-    private char toIndex;
-    private int from;
-    private int to;
+
+    public static final Comparator<InputEdge> OUTGOING_COMPARATOR = new Comparator<InputEdge>(){
+
+        @Override
+            public int compare(InputEdge o1, InputEdge o2) {
+                if(o1.getFromIndex() == o2.getFromIndex()) {
+                    return o1.getTo() - o2.getTo();
+                }
+                return o1.getFromIndex() - o2.getFromIndex();
+            }
+    };
+
+    public static final Comparator<InputEdge> INGOING_COMPARATOR = new Comparator<InputEdge>(){
+
+        @Override
+            public int compare(InputEdge o1, InputEdge o2) {
+                if(o1.getToIndex() == o2.getToIndex()) {
+                    return o1.getFrom() - o2.getFrom();
+                }
+                return o1.getToIndex() - o2.getToIndex();
+            }
+    };
+
+    private final char toIndex;
+    private final char fromIndex;
+    private final int from;
+    private final int to;
+    private final String label;
+    private final String type;
     private State state;
 
     public InputEdge(char toIndex, int from, int to) {
+        this((char) 0, toIndex, from, to, null, null);
+    }
+
+    public InputEdge(char fromIndex, char toIndex, int from, int to) {
+        this(fromIndex, toIndex, from, to, null, null);
+    }
+
+    public InputEdge(char fromIndex, char toIndex, int from, int to, String label, String type) {
         this.toIndex = toIndex;
+        this.fromIndex = fromIndex;
         this.from = from;
         this.to = to;
         this.state = State.SAME;
+        this.label = label;
+        this.type = type.intern();
+    }
+
+    static WeakHashMap<InputEdge, WeakReference<InputEdge>> immutableCache = new WeakHashMap<>();
+
+    public static synchronized InputEdge createImmutable(char fromIndex, char toIndex, int from, int to, String label, String type) {
+        InputEdge edge = new InputEdge(fromIndex, toIndex, from, to, label, type, State.IMMUTABLE);
+        WeakReference<InputEdge> result = immutableCache.get(edge);
+        if (result != null) {
+            InputEdge edge2 = result.get();
+            if (edge2 != null) {
+                return edge2;
+            }
+        }
+        immutableCache.put(edge, new WeakReference<>(edge));
+        return edge;
+    }
+
+    public InputEdge(char fromIndex, char toIndex, int from, int to, String label, String type, State state) {
+        this.toIndex = toIndex;
+        this.fromIndex = fromIndex;
+        this.from = from;
+        this.to = to;
+        this.state = state;
+        this.label = label;
+        this.type = type;
     }
 
     public State getState() {
@@ -52,6 +118,9 @@
     }
 
     public void setState(State x) {
+        if (state == State.IMMUTABLE) {
+            throw new InternalError("Can't change immutable instances");
+        }
         this.state = x;
     }
 
@@ -59,6 +128,10 @@
         return toIndex;
     }
 
+    public char getFromIndex() {
+        return fromIndex;
+    }
+
     public String getName() {
         return "in" + toIndex;
     }
@@ -71,22 +144,35 @@
         return to;
     }
 
+    public String getLabel() {
+        return label;
+    }
+
+    public String getType() {
+        return type;
+    }
+
     @Override
     public boolean equals(Object o) {
         if (o == null || !(o instanceof InputEdge)) {
             return false;
         }
         InputEdge conn2 = (InputEdge) o;
-        return conn2.toIndex == toIndex && conn2.from == from && conn2.to == to;
+        boolean result = conn2.fromIndex == fromIndex && conn2.toIndex == toIndex && conn2.from == from && conn2.to == to;
+        if (result && (state == State.IMMUTABLE || conn2.state == State.IMMUTABLE)) {
+            // Immutable instances must be exactly the same
+            return conn2.label == label && conn2.state == state;
+        }
+        return result;
     }
 
     @Override
     public String toString() {
-        return "Edge from " + from + " to " + to + "(" + (int) toIndex + ") ";
+        return "Edge from " + from + " to " + to + "(" + (int) fromIndex + ", " + (int) toIndex + ") ";
     }
 
     @Override
     public int hashCode() {
-        return (from << 20 | to << 8 | toIndex);
+        return (from << 20 | to << 8 | toIndex << 4 | fromIndex);
     }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/InputGraph.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/InputGraph.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,65 +23,141 @@
  */
 package com.sun.hotspot.igv.data;
 
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.Collections;
-import java.util.HashSet;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Set;
+import java.util.*;
 
 /**
  *
  * @author Thomas Wuerthinger
  */
-public class InputGraph extends Properties.Entity {
+public class InputGraph extends Properties.Entity implements FolderElement {
+
+    private Map<Integer, InputNode> nodes;
+    private List<InputEdge> edges;
+    private Folder parent;
+    private Group parentGroup;
+    private Map<String, InputBlock> blocks;
+    private List<InputBlockEdge> blockEdges;
+    private Map<Integer, InputBlock> nodeToBlock;
+
+    public InputGraph(String name) {
+        setName(name);
+        nodes = new LinkedHashMap<>();
+        edges = new ArrayList<>();
+        blocks = new LinkedHashMap<>();
+        blockEdges = new ArrayList<>();
+        nodeToBlock = new LinkedHashMap<>();
+    }
 
-    private HashMap<Integer, InputNode> nodes;
-    private ArrayList<InputEdge> edges;
-    private Group parent;
-    private HashMap<String, InputBlock> blocks;
-    private HashMap<Integer, InputBlock> nodeToBlock;
-    private boolean isDifferenceGraph;
+    @Override
+    public void setParent(Folder parent) {
+        this.parent = parent;
+        if (parent instanceof Group) {
+            assert this.parentGroup == null;
+            this.parentGroup = (Group) parent;
+        }
+    }
 
-    public InputGraph(Group parent) {
-        this(parent, null);
+    public InputBlockEdge addBlockEdge(InputBlock left, InputBlock right) {
+        InputBlockEdge edge = new InputBlockEdge(left, right);
+        blockEdges.add(edge);
+        left.addSuccessor(right);
+        return edge;
+    }
+
+    public List<InputNode> findRootNodes() {
+        List<InputNode> result = new ArrayList<>();
+        Set<Integer> nonRoot = new HashSet<>();
+        for(InputEdge curEdges : getEdges()) {
+            nonRoot.add(curEdges.getTo());
+        }
+
+        for(InputNode node : getNodes()) {
+            if(!nonRoot.contains(node.getId())) {
+                result.add(node);
+            }
+        }
+
+        return result;
     }
 
-    public InputGraph(Group parent, InputGraph last) {
-        this(parent, last, "");
+    public Map<InputNode, List<InputEdge>> findAllOutgoingEdges() {
+        Map<InputNode, List<InputEdge>> result = new HashMap<>(getNodes().size());
+        for(InputNode n : this.getNodes()) {
+            result.put(n, new ArrayList<InputEdge>());
+        }
+
+        for(InputEdge e : this.edges) {
+            int from = e.getFrom();
+            InputNode fromNode = this.getNode(from);
+            List<InputEdge> fromList = result.get(fromNode);
+            assert fromList != null;
+            fromList.add(e);
+        }
+
+        for(InputNode n : this.getNodes()) {
+            List<InputEdge> list = result.get(n);
+            Collections.sort(list, InputEdge.OUTGOING_COMPARATOR);
+        }
+
+        return result;
     }
 
-    private void clearBlocks() {
+    public Map<InputNode, List<InputEdge>> findAllIngoingEdges() {
+        Map<InputNode, List<InputEdge>> result = new HashMap<>(getNodes().size());
+        for(InputNode n : this.getNodes()) {
+            result.put(n, new ArrayList<InputEdge>());
+        }
+
+        for(InputEdge e : this.edges) {
+            int to = e.getTo();
+            InputNode toNode = this.getNode(to);
+            List<InputEdge> toList = result.get(toNode);
+            assert toList != null;
+            toList.add(e);
+        }
+
+        for(InputNode n : this.getNodes()) {
+            List<InputEdge> list = result.get(n);
+            Collections.sort(list, InputEdge.INGOING_COMPARATOR);
+        }
+
+        return result;
+    }
+
+    public List<InputEdge> findOutgoingEdges(InputNode n) {
+        List<InputEdge> result = new ArrayList<>();
+
+        for(InputEdge e : this.edges) {
+            if(e.getFrom() == n.getId()) {
+                result.add(e);
+            }
+        }
+
+        Collections.sort(result, InputEdge.OUTGOING_COMPARATOR);
+
+        return result;
+    }
+
+    public void clearBlocks() {
         blocks.clear();
         nodeToBlock.clear();
     }
 
-    public InputGraph(Group parent, InputGraph last, String name) {
-        this.parent = parent;
-        setName(name);
-        nodes = new HashMap<Integer, InputNode>();
-        edges = new ArrayList<InputEdge>();
-        blocks = new HashMap<String, InputBlock>();
-        nodeToBlock = new HashMap<Integer, InputBlock>();
-        if (last != null) {
+    public void setEdge(int fromIndex, int toIndex, int from, int to) {
+        assert fromIndex == ((char)fromIndex) : "Downcast must be safe";
+        assert toIndex == ((char)toIndex) : "Downcast must be safe";
 
-            for (InputNode n : last.getNodes()) {
-                addNode(n);
-            }
-
-            for (InputEdge c : last.getEdges()) {
-                addEdge(c);
-            }
+        InputEdge edge = new InputEdge((char)fromIndex, (char)toIndex, from, to);
+        if(!this.getEdges().contains(edge)) {
+            this.addEdge(edge);
         }
     }
 
-    public void schedule(Collection<InputBlock> newBlocks) {
-        clearBlocks();
-        InputBlock noBlock = new InputBlock(this, "no block");
-        Set<InputNode> scheduledNodes = new HashSet<InputNode>();
+    public void ensureNodesInBlocks() {
+        InputBlock noBlock = null;
+        Set<InputNode> scheduledNodes = new HashSet<>();
 
-        for (InputBlock b : newBlocks) {
+        for (InputBlock b : getBlocks()) {
             for (InputNode n : b.getNodes()) {
                 assert !scheduledNodes.contains(n);
                 scheduledNodes.add(n);
@@ -91,18 +167,11 @@
         for (InputNode n : this.getNodes()) {
             assert nodes.get(n.getId()) == n;
             if (!scheduledNodes.contains(n)) {
+                if (noBlock == null) {
+                    noBlock = this.addBlock("(no block)");
+                }
                 noBlock.addNode(n.getId());
             }
-        }
-
-        if (noBlock.getNodes().size() != 0) {
-            newBlocks.add(noBlock);
-        }
-        for (InputBlock b : newBlocks) {
-            addBlock(b);
-        }
-
-        for (InputNode n : this.getNodes()) {
             assert this.getBlock(n) != null;
         }
     }
@@ -116,45 +185,26 @@
     }
 
     public InputBlock getBlock(InputNode node) {
+        assert nodes.containsKey(node.getId());
+        assert nodes.get(node.getId()).equals(node);
         return getBlock(node.getId());
     }
 
     public InputGraph getNext() {
-        List<InputGraph> list = parent.getGraphs();
-        if (!list.contains(this)) {
-            return null;
-        }
-        int index = list.indexOf(this);
-        if (index == list.size() - 1) {
-            return null;
-        } else {
-            return list.get(index + 1);
-        }
+        return parentGroup.getNext(this);
     }
 
     public InputGraph getPrev() {
-        List<InputGraph> list = parent.getGraphs();
-        if (!list.contains(this)) {
-            return null;
-        }
-        int index = list.indexOf(this);
-        if (index == 0) {
-            return null;
-        } else {
-            return list.get(index - 1);
-        }
+        return parentGroup.getPrev(this);
     }
 
-    public String getName() {
-        return getProperties().get("name");
+    private void setName(String name) {
+        this.getProperties().setProperty("name", name);
     }
 
-    public String getAbsoluteName() {
-        String result = getName();
-        if (this.parent != null) {
-            result = parent.getName() + ": " + result;
-        }
-        return result;
+    @Override
+    public String getName() {
+        return getProperties().get("name");
     }
 
     public Collection<InputNode> getNodes() {
@@ -186,25 +236,22 @@
     }
 
     public void removeEdge(InputEdge c) {
-        assert edges.contains(c);
-        edges.remove(c);
-        assert !edges.contains(c);
+        boolean removed = edges.remove(c);
+        assert removed;
     }
 
     public void addEdge(InputEdge c) {
-        assert !edges.contains(c);
         edges.add(c);
-        assert edges.contains(c);
     }
 
     public Group getGroup() {
-        return parent;
+        return parentGroup;
     }
 
     @Override
     public String toString() {
         StringBuilder sb = new StringBuilder();
-        sb.append("Graph " + getName() + " " + getProperties().toString() + "\n");
+        sb.append("Graph ").append(getName()).append(" ").append(getProperties().toString()).append("\n");
         for (InputNode n : nodes.values()) {
             sb.append(n.toString());
             sb.append("\n");
@@ -214,35 +261,31 @@
             sb.append(c.toString());
             sb.append("\n");
         }
+
+        for (InputBlock b : getBlocks()) {
+            sb.append(b.toString());
+            sb.append("\n");
+        }
+
         return sb.toString();
     }
 
-    public void addBlock(InputBlock b) {
+    public InputBlock addBlock(String name) {
+        final InputBlock b = new InputBlock(this, name);
         blocks.put(b.getName(), b);
-        for (InputNode n : b.getNodes()) {
-            this.nodeToBlock.put(n.getId(), b);
-        }
-    }
-
-    public void resolveBlockLinks() {
-        for (InputBlock b : blocks.values()) {
-            b.resolveBlockLinks();
-        }
-    }
-
-    public void setName(String s) {
-        getProperties().setProperty("name", s);
+        return b;
     }
 
     public InputBlock getBlock(String s) {
         return blocks.get(s);
     }
 
-    public boolean isDifferenceGraph() {
-        return this.isDifferenceGraph;
+    public Collection<InputBlockEdge> getBlockEdges() {
+        return Collections.unmodifiableList(blockEdges);
     }
 
-    public void setIsDifferenceGraph(boolean b) {
-        isDifferenceGraph = b;
+    @Override
+    public Folder getParent() {
+        return parent;
     }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/InputMethod.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/InputMethod.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,10 +23,11 @@
  */
 package com.sun.hotspot.igv.data;
 
-import com.sun.hotspot.igv.data.Properties;
 import java.util.ArrayList;
 import java.util.Collections;
 import java.util.List;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
 
 /**
  *
@@ -42,14 +43,37 @@
     private Group group;
     private List<InputBytecode> bytecodes;
 
+    @Override
+    public int hashCode() {
+        int result = name.hashCode();
+        result = result * 31 + bci;
+        result = result * 31 + shortName.hashCode();
+        result = result * 31 + inlined.hashCode();
+        result = result * 31 + bytecodes.hashCode();
+        return result;
+    }
+
+    @Override
+    public boolean equals(Object o) {
+        if (o == null || (!(o instanceof InputMethod))) {
+            return false;
+        }
+
+        final InputMethod im = (InputMethod)o;
+        return name.equals(im.name) && bci == im.bci && shortName.equals(im.shortName) &&
+               inlined.equals(im.inlined) && bytecodes.equals(im.bytecodes);
+    }
+
+
+
     /** Creates a new instance of InputMethod */
     public InputMethod(Group parent, String name, String shortName, int bci) {
         this.group = parent;
         this.name = name;
         this.bci = bci;
         this.shortName = shortName;
-        inlined = new ArrayList<InputMethod>();
-        bytecodes = new ArrayList<InputBytecode>();
+        inlined = new ArrayList<>();
+        bytecodes = new ArrayList<>();
     }
 
     public List<InputBytecode> getBytecodes() {
@@ -87,31 +111,42 @@
     }
 
     public void setBytecodes(String text) {
-
+        Pattern instruction = Pattern.compile("\\s*(\\d+)\\s*:?\\s*(\\w+)\\s*(.*)(?://(.*))?");
         String[] strings = text.split("\n");
-        int oldNumber = -1;
+        int oldBci = -1;
         for (String s : strings) {
-
-            if (s.length() > 0 && Character.isDigit(s.charAt(0))) {
-                s = s.trim();
-                int spaceIndex = s.indexOf(' ');
-                String numberString = s.substring(0, spaceIndex);
-                String tmpName = s.substring(spaceIndex + 1, s.length());
+            if (s.startsWith(" ")) {
+                // indented lines are extra textual information
+                continue;
+            }
+            s = s.trim();
+            if (s.length() != 0) {
+                final Matcher matcher = instruction.matcher(s);
+                if (matcher.matches()) {
+                    String bciString = matcher.group(1);
+                    String opcode = matcher.group(2);
+                    String operands = matcher.group(3).trim();
+                    String comment = matcher.group(4);
+                    if (comment != null) {
+                        comment = comment.trim();
+                    }
 
-                int number = -1;
-                number = Integer.parseInt(numberString);
+                    int bci = Integer.parseInt(bciString);
 
-                // assert correct order of bytecodes
-                assert number > oldNumber;
+                    // assert correct order of bytecodes
+                    assert bci > oldBci;
+
+                    InputBytecode bc = new InputBytecode(bci, opcode, operands, comment);
+                    bytecodes.add(bc);
 
-                InputBytecode bc = new InputBytecode(number, tmpName);
-                bytecodes.add(bc);
-
-                for (InputMethod m : inlined) {
-                    if (m.getBci() == number) {
-                        bc.setInlined(m);
-                        break;
+                    for (InputMethod m : inlined) {
+                        if (m.getBci() == bci) {
+                            bc.setInlined(m);
+                            break;
+                        }
                     }
+                } else {
+                    System.out.println("no match: " + s);
                 }
             }
         }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/InputNode.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/InputNode.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,6 +23,10 @@
  */
 package com.sun.hotspot.igv.data;
 
+import java.util.ArrayList;
+import java.util.Comparator;
+import java.util.List;
+
 /**
  *
  * @author Thomas Wuerthinger
@@ -30,6 +34,37 @@
 public class InputNode extends Properties.Entity {
 
     private int id;
+    private List<InputGraph> subgraphs;
+
+    public static final Comparator<InputNode> COMPARATOR = new Comparator<InputNode>() {
+        @Override
+        public int compare(InputNode o1, InputNode o2) {
+            return o1.getId() - o2.getId();
+        }
+    };
+
+    public static Comparator<InputNode> getPropertyComparator(final String propertyName) {
+        return new Comparator<InputNode>() {
+
+            @Override
+            public int compare(InputNode o1, InputNode o2) {
+
+                int i1 = 0;
+                try {
+                    i1 = Integer.parseInt(o1.getProperties().get(propertyName));
+                } catch(NumberFormatException e) {
+                }
+
+                int i2 = 0;
+                try {
+                    i2 = Integer.parseInt(o2.getProperties().get(propertyName));
+                } catch(NumberFormatException e) {
+                }
+
+                return i1 - i2;
+            }
+        };
+    }
 
     public InputNode(InputNode n) {
         super(n);
@@ -49,21 +84,29 @@
         return id;
     }
 
+    public void addSubgraph(InputGraph graph) {
+        if (subgraphs == null) {
+            subgraphs = new ArrayList<>();
+        }
+        subgraphs.add(graph);
+    }
+
+    public List<InputGraph> getSubgraphs() {
+        return subgraphs;
+    }
+
     @Override
     public boolean equals(Object o) {
         if (!(o instanceof InputNode)) {
             return false;
         }
         InputNode n = (InputNode) o;
-        if (n.id != id) {
-            return false;
-        }
-        return getProperties().equals(n.getProperties());
+        return n.id == id;
     }
 
     @Override
     public int hashCode() {
-        return id;
+        return id * 13;
     }
 
     @Override
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/Pair.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/Pair.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -58,15 +58,30 @@
 
     @Override
     public boolean equals(Object o) {
-        if (!(o instanceof Pair)) {
+        if (o == null || !(o instanceof Pair)) {
             return false;
         }
-        Pair obj = (Pair) o;
-        return l.equals(obj.l) && r.equals(obj.r);
+        Pair<?,?> obj = (Pair<?,?>) o;
+        boolean b1 = (l == obj.l);
+        if (l != null) {
+            b1 = l.equals(obj.l);
+        }
+
+        boolean b2 = (r == obj.r);
+        if (r != null) {
+            b2 = r.equals(obj.r);
+        }
+
+        return b1 && b2;
     }
 
     @Override
     public int hashCode() {
-        return l.hashCode() * 71 + r.hashCode();
+        return ((l == null) ? 0 : l.hashCode()) * 71 + ((r == null) ? 0 : r.hashCode());
+    }
+
+    @Override
+    public String toString() {
+        return "[" + l + "/" + r + "]";
     }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/Properties.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/Properties.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -24,13 +24,10 @@
 package com.sun.hotspot.igv.data;
 
 import java.io.Serializable;
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.Iterator;
-import java.util.List;
+import java.util.*;
 import java.util.regex.Matcher;
 import java.util.regex.Pattern;
-
+import java.util.regex.PatternSyntaxException;
 
 /**
  *
@@ -58,13 +55,30 @@
                 return false;
             }
         }
+
+        for (Property prop : p) {
+            String value = this.get(prop.getName());
+            if (value == null || !value.equals(prop.getValue())) {
+                return false;
+            }
+        }
+
         return true;
     }
 
     @Override
     public int hashCode() {
         int hash = 5;
-        hash = 83 * hash + (this.map != null ? this.map.hashCode() : 0);
+
+        if (map != null) {
+            for (int i = 0; i < this.map.length; i++) {
+                if (map[i] == null) {
+                    i++;
+                } else {
+                    hash = hash * 83 + map[i].hashCode();
+                }
+            }
+        }
         return hash;
     }
 
@@ -85,7 +99,7 @@
 
     public Properties(Properties p) {
         map = new String[p.map.length];
-        System.arraycopy(map, 0, p.map, 0, p.map.length);
+        System.arraycopy(p.map, 0, map, 0, p.map.length);
     }
 
     public static class Entity implements Provider {
@@ -100,19 +114,12 @@
             properties = new Properties(object.getProperties());
         }
 
+        @Override
         public Properties getProperties() {
             return properties;
         }
     }
 
-    private String getProperty(String key) {
-        for (int i = 0; i < map.length; i += 2)
-            if (map[i] != null && map[i].equals(key)) {
-                return map[i + 1];
-            }
-        return null;
-    }
-
     public interface PropertyMatcher {
 
         String getName();
@@ -128,11 +135,16 @@
             this.matcher = matcher;
         }
 
+        @Override
         public String getName() {
             return matcher.getName();
         }
 
+        @Override
         public boolean match(String p) {
+            if (p == null) {
+                return false;
+            }
             return !matcher.match(p);
         }
     }
@@ -143,15 +155,26 @@
         private String value;
 
         public StringPropertyMatcher(String name, String value) {
+            if (name == null) {
+                throw new IllegalArgumentException("Property name must not be null!");
+            }
+            if (value == null) {
+                throw new IllegalArgumentException("Property value must not be null!");
+            }
             this.name = name;
             this.value = value;
         }
 
+        @Override
         public String getName() {
             return name;
         }
 
+        @Override
         public boolean match(String p) {
+            if (p == null) {
+                throw new IllegalArgumentException("Property value must not be null!");
+            }
             return p.equals(value);
         }
     }
@@ -162,30 +185,55 @@
         private Pattern valuePattern;
 
         public RegexpPropertyMatcher(String name, String value) {
-            this.name = name;
-            valuePattern = Pattern.compile(value);
+            this(name, value, 0);
         }
 
+        public RegexpPropertyMatcher(String name, String value, int flags) {
+
+            if (name == null) {
+                throw new IllegalArgumentException("Property name must not be null!");
+            }
+
+            if (value == null) {
+                throw new IllegalArgumentException("Property value pattern must not be null!");
+            }
+
+            this.name = name;
+
+            try {
+                valuePattern = Pattern.compile(value, flags);
+            } catch (PatternSyntaxException e) {
+                throw new IllegalArgumentException("Bad pattern: " + value);
+            }
+        }
+
+        @Override
         public String getName() {
             return name;
         }
 
+        @Override
         public boolean match(String p) {
+            if (p == null) {
+                throw new IllegalArgumentException("Property value must not be null!");
+            }
             Matcher m = valuePattern.matcher(p);
             return m.matches();
         }
     }
 
     public Property selectSingle(PropertyMatcher matcher) {
+
+        final String name = matcher.getName();
         String value = null;
         for (int i = 0; i < map.length; i += 2) {
-            if (map[i] != null && matcher.getName().equals(map[i]))  {
+            if (map[i] != null && name.equals(map[i])) {
                 value = map[i + 1];
                 break;
             }
         }
         if (value != null && matcher.match(value)) {
-            return new Property(matcher.getName(), value);
+            return new Property(name, value);
         } else {
             return null;
         }
@@ -198,13 +246,32 @@
 
     @Override
     public String toString() {
-        StringBuilder sb = new StringBuilder();
-        sb.append("[");
+        List<String[]> pairs = new ArrayList<>();
         for (int i = 0; i < map.length; i += 2) {
             if (map[i + 1] != null) {
-                String p = map[i + 1];
-                sb.append(map[i] + " = " + map[i + 1] + "; ");
+                pairs.add(new String[]{map[i], map[i + 1]});
+            }
+        }
+
+        Collections.sort(pairs, new Comparator<String[]>() {
+            @Override
+            public int compare(String[] o1, String[] o2) {
+                assert o1.length == 2;
+                assert o2.length == 2;
+                return o1[0].compareTo(o2[0]);
             }
+        });
+
+        StringBuilder sb = new StringBuilder();
+        sb.append("[");
+        boolean first = true;
+        for (String[] p : pairs) {
+            if (first) {
+                first = false;
+            } else {
+                sb.append(", ");
+            }
+            sb.append(p[0]).append("=").append(p[1]);
         }
         return sb.append("]").toString();
     }
@@ -217,10 +284,6 @@
             this.objects = objects;
         }
 
-        public T selectSingle(final String name, final String value) {
-            return selectSingle(new StringPropertyMatcher(name, value));
-        }
-
         public T selectSingle(PropertyMatcher matcher) {
 
             for (T t : objects) {
@@ -233,18 +296,16 @@
             return null;
         }
 
-        public List<T> selectMultiple(final String name, final String value) {
-            return selectMultiple(new StringPropertyMatcher(name, value));
-        }
+        public List<T> selectMultiple(PropertyMatcher matcher) {
+            List<T> result = new ArrayList<>();
 
-        public List<T> selectMultiple(PropertyMatcher matcher) {
-            List<T> result = new ArrayList<T>();
             for (T t : objects) {
                 Property p = t.getProperties().selectSingle(matcher);
                 if (p != null) {
                     result.add(t);
                 }
             }
+
             return result;
         }
     }
@@ -259,6 +320,10 @@
     }
 
     public void setProperty(String name, String value) {
+        setPropertyInternal(name.intern(), value != null ? value.intern() : null);
+    }
+    private void setPropertyInternal(String name, String value) {
+
         for (int i = 0; i < map.length; i += 2) {
             if (map[i] != null && map[i].equals(name)) {
                 String p = map[i + 1];
@@ -289,34 +354,26 @@
         map = newMap;
     }
 
-    public  Iterator<Property> getProperties() {
-        return iterator();
-    }
-
     public void add(Properties properties) {
         for (Property p : properties) {
-            add(p);
+            // Already interned
+            setPropertyInternal(p.getName(), p.getValue());
         }
     }
 
-    public void add(Property property) {
-        assert property.getName() != null;
-        assert property.getValue() != null;
-        setProperty(property.getName(), property.getValue());
-    }
-    class PropertiesIterator implements Iterator<Property>, Iterable<Property> {
-        public Iterator<Property> iterator() {
-                return this;
-        }
+    private class PropertiesIterator implements Iterator<Property> {
 
         int index;
 
+        @Override
         public boolean hasNext() {
-            while (index < map.length && map[index + 1] == null)
+            while (index < map.length && map[index + 1] == null) {
                 index += 2;
+            }
             return index < map.length;
         }
 
+        @Override
         public Property next() {
             if (index < map.length) {
                 index += 2;
@@ -325,11 +382,13 @@
             return null;
         }
 
+        @Override
         public void remove() {
             throw new UnsupportedOperationException("Not supported yet.");
         }
+    }
 
-    }
+    @Override
     public Iterator<Property> iterator() {
         return new PropertiesIterator();
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/Property.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/Property.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -32,25 +32,20 @@
 public class Property implements Serializable {
 
     public static final long serialVersionUID = 1L;
-
     private String name;
     private String value;
 
-    private Property() {
-        this(null, null);
-    }
-
-    private Property(Property p) {
-        this(p.getName(), p.getValue());
-    }
-
-    private Property(String name) {
-        this(name, null);
-    }
-
-    public Property(String name, String value) {
+    Property(String name, String value) {
         this.name = name;
         this.value = value;
+
+        if (value == null) {
+            throw new IllegalArgumentException("Property value must not be null!");
+        }
+
+        if (name == null) {
+            throw new IllegalArgumentException("Property name must not be null!");
+        }
     }
 
     public String getName() {
@@ -63,17 +58,20 @@
 
     @Override
     public String toString() {
-        return name + " = " + value + "; ";
+        return name + "=" + value;
     }
 
     @Override
     public boolean equals(Object o) {
-        if (!(o instanceof Property)) return false;
-        Property p2 = (Property)o;
+        if (!(o instanceof Property)) {
+            return false;
+        }
+        Property p2 = (Property) o;
         return name.equals(p2.name) && value.equals(p2.value);
     }
+
     @Override
     public int hashCode() {
-        return name.hashCode() + value == null ? 0 : value.hashCode();
+        return name.hashCode() * 13 + value.hashCode();
     }
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/Source.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,67 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+package com.sun.hotspot.igv.data;
+
+import java.util.*;
+
+/**
+ *
+ * @author Thomas Wuerthinger
+ */
+public class Source {
+
+    private List<InputNode> sourceNodes;
+    private Set<Integer> set;
+
+    public Source() {
+        sourceNodes = new ArrayList<>(1);
+        set = new LinkedHashSet<>(1);
+    }
+
+    public List<InputNode> getSourceNodes() {
+        return Collections.unmodifiableList(sourceNodes);
+    }
+
+    public Set<Integer> getSourceNodesAsSet() {
+        return Collections.unmodifiableSet(set);
+    }
+
+    public void addSourceNode(InputNode n) {
+        if (!set.contains(n.getId())) {
+            sourceNodes.add(n);
+            set.add(n.getId());
+        }
+    }
+
+    public interface Provider {
+
+        public Source getSource();
+    }
+
+    public void addSourceNodes(Source s) {
+        for (InputNode n : s.getSourceNodes()) {
+            addSourceNode(n);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/serialization/BinaryParser.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,900 @@
+/*
+ * 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.
+ */
+package com.sun.hotspot.igv.data.serialization;
+
+import com.sun.hotspot.igv.data.*;
+import com.sun.hotspot.igv.data.Properties;
+import com.sun.hotspot.igv.data.services.GroupCallback;
+import java.io.EOFException;
+import java.io.IOException;
+import java.nio.ByteBuffer;
+import java.nio.channels.ReadableByteChannel;
+import java.util.*;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+import javax.swing.SwingUtilities;
+import java.security.MessageDigest;
+import java.security.NoSuchAlgorithmException;
+
+public class BinaryParser implements GraphParser {
+    private static final int BEGIN_GROUP = 0x00;
+    private static final int BEGIN_GRAPH = 0x01;
+    private static final int CLOSE_GROUP = 0x02;
+
+    private static final int POOL_NEW = 0x00;
+    private static final int POOL_STRING = 0x01;
+    private static final int POOL_ENUM = 0x02;
+    private static final int POOL_CLASS = 0x03;
+    private static final int POOL_METHOD = 0x04;
+    private static final int POOL_NULL = 0x05;
+    private static final int POOL_NODE_CLASS = 0x06;
+    private static final int POOL_FIELD = 0x07;
+    private static final int POOL_SIGNATURE = 0x08;
+
+    private static final int KLASS = 0x00;
+    private static final int ENUM_KLASS = 0x01;
+
+    private static final int PROPERTY_POOL = 0x00;
+    private static final int PROPERTY_INT = 0x01;
+    private static final int PROPERTY_LONG = 0x02;
+    private static final int PROPERTY_DOUBLE = 0x03;
+    private static final int PROPERTY_FLOAT = 0x04;
+    private static final int PROPERTY_TRUE = 0x05;
+    private static final int PROPERTY_FALSE = 0x06;
+    private static final int PROPERTY_ARRAY = 0x07;
+    private static final int PROPERTY_SUBGRAPH = 0x08;
+
+    private static final String NO_BLOCK = "noBlock";
+
+    private final GroupCallback callback;
+    private final List<Object> constantPool;
+    private final ByteBuffer buffer;
+    private final ReadableByteChannel channel;
+    private final GraphDocument rootDocument;
+    private final Deque<Folder> folderStack;
+    private final Deque<byte[]> hashStack;
+    private final ParseMonitor monitor;
+
+    private MessageDigest digest;
+
+    private enum Length {
+        S,
+        M,
+        L
+    }
+
+    private interface LengthToString {
+        String toString(Length l);
+    }
+
+    private static abstract class Member implements LengthToString {
+        public final Klass holder;
+        public final int accessFlags;
+        public final String name;
+        public Member(Klass holder, String name, int accessFlags) {
+            this.holder = holder;
+            this.accessFlags = accessFlags;
+            this.name = name;
+        }
+    }
+
+    private static class Method extends Member {
+        public final Signature signature;
+        public final byte[] code;
+        public Method(String name, Signature signature, byte[] code, Klass holder, int accessFlags) {
+            super(holder, name, accessFlags);
+            this.signature = signature;
+            this.code = code;
+        }
+        @Override
+        public String toString() {
+            StringBuilder sb = new StringBuilder();
+            sb.append(holder).append('.').append(name).append('(');
+            for (int i = 0; i < signature.argTypes.length; i++) {
+                if (i > 0) {
+                    sb.append(", ");
+                }
+                sb.append(signature.argTypes[i]);
+            }
+            sb.append(')');
+            return sb.toString();
+        }
+        @Override
+        public String toString(Length l) {
+            switch(l) {
+                case M:
+                    return holder.toString(Length.L) + "." + name;
+                case S:
+                    return holder.toString(Length.S) + "." + name;
+                default:
+                case L:
+                    return toString();
+            }
+        }
+    }
+
+    private static class Signature {
+        public final String returnType;
+        public final String[] argTypes;
+        public Signature(String returnType, String[] argTypes) {
+            this.returnType = returnType;
+            this.argTypes = argTypes;
+        }
+    }
+
+    private static class Field extends Member {
+        public final String type;
+        public Field(String type, Klass holder, String name, int accessFlags) {
+            super(holder, name, accessFlags);
+            this.type = type;
+        }
+        @Override
+        public String toString() {
+            return holder + "." + name;
+        }
+        @Override
+        public String toString(Length l) {
+            switch(l) {
+                case M:
+                    return holder.toString(Length.L) + "." + name;
+                case S:
+                    return holder.toString(Length.S) + "." + name;
+                default:
+                case L:
+                    return toString();
+            }
+        }
+    }
+
+    private static class Klass implements LengthToString {
+        public final String name;
+        public final String simpleName;
+        public Klass(String name) {
+            this.name = name;
+            String simple;
+            try {
+                simple = name.substring(name.lastIndexOf('.') + 1);
+            } catch (IndexOutOfBoundsException ioobe) {
+                simple = name;
+            }
+            this.simpleName = simple;
+        }
+        @Override
+        public String toString() {
+            return name;
+        }
+        @Override
+        public String toString(Length l) {
+            switch(l) {
+                case S:
+                    return simpleName;
+                default:
+                case L:
+                case M:
+                    return toString();
+            }
+        }
+    }
+
+    private static class EnumKlass extends Klass {
+        public final String[] values;
+        public EnumKlass(String name, String[] values) {
+            super(name);
+            this.values = values;
+        }
+    }
+
+    private static class Port {
+        public final boolean isList;
+        public final String name;
+        private Port(boolean isList, String name) {
+            this.isList = isList;
+            this.name = name;
+        }
+    }
+
+    private static class TypedPort extends Port {
+        public final EnumValue type;
+        private TypedPort(boolean isList, String name, EnumValue type) {
+            super(isList, name);
+            this.type = type;
+        }
+    }
+
+    private static class NodeClass {
+        public final String className;
+        public final String nameTemplate;
+        public final List<TypedPort> inputs;
+        public final List<Port> sux;
+        private NodeClass(String className, String nameTemplate, List<TypedPort> inputs, List<Port> sux) {
+            this.className = className;
+            this.nameTemplate = nameTemplate;
+            this.inputs = inputs;
+            this.sux = sux;
+        }
+        @Override
+        public String toString() {
+            return className;
+        }
+    }
+
+    private static class EnumValue implements LengthToString {
+        public EnumKlass enumKlass;
+        public int ordinal;
+        public EnumValue(EnumKlass enumKlass, int ordinal) {
+            this.enumKlass = enumKlass;
+            this.ordinal = ordinal;
+        }
+        @Override
+        public String toString() {
+            return enumKlass.simpleName + "." + enumKlass.values[ordinal];
+        }
+        @Override
+        public String toString(Length l) {
+            switch(l) {
+                case S:
+                    return enumKlass.values[ordinal];
+                default:
+                case M:
+                case L:
+                    return toString();
+            }
+        }
+    }
+
+    public BinaryParser(ReadableByteChannel channel, ParseMonitor monitor, GraphDocument rootDocument, GroupCallback callback) {
+        this.callback = callback;
+        constantPool = new ArrayList<>();
+        buffer = ByteBuffer.allocateDirect(256 * 1024);
+        buffer.flip();
+        this.channel = channel;
+        this.rootDocument = rootDocument;
+        folderStack = new LinkedList<>();
+        hashStack = new LinkedList<>();
+        this.monitor = monitor;
+        try {
+            this.digest = MessageDigest.getInstance("SHA-256");
+        } catch (NoSuchAlgorithmException e) {
+        }
+    }
+
+    private void fill() throws IOException {
+        buffer.compact();
+        if (channel.read(buffer) < 0) {
+            throw new EOFException();
+        }
+        buffer.flip();
+    }
+
+    private void ensureAvailable(int i) throws IOException {
+        while (buffer.remaining() < i) {
+            fill();
+        }
+        buffer.mark();
+        byte[] result = new byte[i];
+        buffer.get(result);
+        digest.update(result);
+        buffer.reset();
+    }
+
+    private int readByte() throws IOException {
+        ensureAvailable(1);
+        return ((int)buffer.get()) & 0xff;
+    }
+
+    private int readInt() throws IOException {
+        ensureAvailable(4);
+        return buffer.getInt();
+    }
+
+    private char readShort() throws IOException {
+        ensureAvailable(2);
+        return buffer.getChar();
+    }
+
+    private long readLong() throws IOException {
+        ensureAvailable(8);
+        return buffer.getLong();
+    }
+
+    private double readDouble() throws IOException {
+        ensureAvailable(8);
+        return buffer.getDouble();
+    }
+
+    private float readFloat() throws IOException {
+        ensureAvailable(4);
+        return buffer.getFloat();
+    }
+
+    private String readString() throws IOException {
+        int len = readInt();
+        ensureAvailable(len * 2);
+        char[] chars = new char[len];
+        buffer.asCharBuffer().get(chars);
+        buffer.position(buffer.position() + len * 2);
+        return new String(chars).intern();
+    }
+
+    private byte[] readBytes() throws IOException {
+        int len = readInt();
+        if (len < 0) {
+            return null;
+        }
+        ensureAvailable(len);
+        byte[] data = new byte[len];
+        buffer.get(data);
+        return data;
+    }
+
+    private String readIntsToString() throws IOException {
+        int len = readInt();
+        if (len < 0) {
+            return "null";
+        }
+        ensureAvailable(len * 4);
+        StringBuilder sb = new StringBuilder().append('[');
+        for (int i = 0; i < len; i++) {
+            sb.append(buffer.getInt());
+            if (i < len - 1) {
+                sb.append(", ");
+            }
+        }
+        sb.append(']');
+        return sb.toString().intern();
+    }
+
+    private String readDoublesToString() throws IOException {
+        int len = readInt();
+        if (len < 0) {
+            return "null";
+        }
+        ensureAvailable(len * 8);
+        StringBuilder sb = new StringBuilder().append('[');
+        for (int i = 0; i < len; i++) {
+            sb.append(buffer.getDouble());
+            if (i < len - 1) {
+                sb.append(", ");
+            }
+        }
+        sb.append(']');
+        return sb.toString().intern();
+    }
+
+    private String readPoolObjectsToString() throws IOException {
+        int len = readInt();
+        if (len < 0) {
+            return "null";
+        }
+        StringBuilder sb = new StringBuilder().append('[');
+        for (int i = 0; i < len; i++) {
+            sb.append(readPoolObject(Object.class));
+            if (i < len - 1) {
+                sb.append(", ");
+            }
+        }
+        sb.append(']');
+        return sb.toString().intern();
+    }
+
+    private <T> T readPoolObject(Class<T> klass) throws IOException {
+        int type = readByte();
+        if (type == POOL_NULL) {
+            return null;
+        }
+        if (type == POOL_NEW) {
+            return (T) addPoolEntry(klass);
+        }
+        assert assertObjectType(klass, type);
+        char index = readShort();
+        if (index < 0 || index >= constantPool.size()) {
+            throw new IOException("Invalid constant pool index : " + index);
+        }
+        Object obj = constantPool.get(index);
+        return (T) obj;
+    }
+
+    private boolean assertObjectType(Class<?> klass, int type) {
+        switch(type) {
+            case POOL_CLASS:
+                return klass.isAssignableFrom(EnumKlass.class);
+            case POOL_ENUM:
+                return klass.isAssignableFrom(EnumValue.class);
+            case POOL_METHOD:
+                return klass.isAssignableFrom(Method.class);
+            case POOL_STRING:
+                return klass.isAssignableFrom(String.class);
+            case POOL_NODE_CLASS:
+                return klass.isAssignableFrom(NodeClass.class);
+            case POOL_FIELD:
+                return klass.isAssignableFrom(Field.class);
+            case POOL_SIGNATURE:
+                return klass.isAssignableFrom(Signature.class);
+            case POOL_NULL:
+                return true;
+            default:
+                return false;
+        }
+    }
+
+    private Object addPoolEntry(Class<?> klass) throws IOException {
+        char index = readShort();
+        int type = readByte();
+        assert assertObjectType(klass, type) : "Wrong object type : " + klass + " != " + type;
+        Object obj;
+        switch(type) {
+            case POOL_CLASS: {
+                String name = readString();
+                int klasstype = readByte();
+                if (klasstype == ENUM_KLASS) {
+                    int len = readInt();
+                    String[] values = new String[len];
+                    for (int i = 0; i < len; i++) {
+                        values[i] = readPoolObject(String.class);
+                    }
+                    obj = new EnumKlass(name, values);
+                } else if (klasstype == KLASS) {
+                    obj = new Klass(name);
+                } else {
+                    throw new IOException("unknown klass type : " + klasstype);
+                }
+                break;
+            }
+            case POOL_ENUM: {
+                EnumKlass enumClass = readPoolObject(EnumKlass.class);
+                int ordinal = readInt();
+                obj = new EnumValue(enumClass, ordinal);
+                break;
+            }
+            case POOL_NODE_CLASS: {
+                String className = readString();
+                String nameTemplate = readString();
+                int inputCount = readShort();
+                List<TypedPort> inputs = new ArrayList<>(inputCount);
+                for (int i = 0; i < inputCount; i++) {
+                    boolean isList = readByte() != 0;
+                    String name = readPoolObject(String.class);
+                    EnumValue inputType = readPoolObject(EnumValue.class);
+                    inputs.add(new TypedPort(isList, name, inputType));
+                }
+                int suxCount = readShort();
+                List<Port> sux = new ArrayList<>(suxCount);
+                for (int i = 0; i < suxCount; i++) {
+                    boolean isList = readByte() != 0;
+                    String name = readPoolObject(String.class);
+                    sux.add(new Port(isList, name));
+                }
+                obj = new NodeClass(className, nameTemplate, inputs, sux);
+                break;
+            }
+            case POOL_METHOD: {
+                Klass holder = readPoolObject(Klass.class);
+                String name = readPoolObject(String.class);
+                Signature sign = readPoolObject(Signature.class);
+                int flags = readInt();
+                byte[] code = readBytes();
+                obj = new Method(name, sign, code, holder, flags);
+                break;
+            }
+            case POOL_FIELD: {
+                Klass holder = readPoolObject(Klass.class);
+                String name = readPoolObject(String.class);
+                String fType = readPoolObject(String.class);
+                int flags = readInt();
+                obj = new Field(fType, holder, name, flags);
+                break;
+            }
+            case POOL_SIGNATURE: {
+                int argc = readShort();
+                String[] args = new String[argc];
+                for (int i = 0; i < argc; i++) {
+                    args[i] = readPoolObject(String.class);
+                }
+                String returnType = readPoolObject(String.class);
+                obj = new Signature(returnType, args);
+                break;
+            }
+            case POOL_STRING: {
+                obj = readString();
+                break;
+            }
+            default:
+                throw new IOException("unknown pool type");
+        }
+        while (constantPool.size() <= index) {
+            constantPool.add(null);
+        }
+        constantPool.set(index, obj);
+        return obj;
+    }
+
+    private Object readPropertyObject() throws IOException {
+        int type = readByte();
+        switch (type) {
+            case PROPERTY_INT:
+                return readInt();
+            case PROPERTY_LONG:
+                return readLong();
+            case PROPERTY_FLOAT:
+                return readFloat();
+            case PROPERTY_DOUBLE:
+                return readDouble();
+            case PROPERTY_TRUE:
+                return Boolean.TRUE;
+            case PROPERTY_FALSE:
+                return Boolean.FALSE;
+            case PROPERTY_POOL:
+                return readPoolObject(Object.class);
+            case PROPERTY_ARRAY:
+                int subType = readByte();
+                switch(subType) {
+                    case PROPERTY_INT:
+                        return readIntsToString();
+                    case PROPERTY_DOUBLE:
+                        return readDoublesToString();
+                    case PROPERTY_POOL:
+                        return readPoolObjectsToString();
+                    default:
+                        throw new IOException("Unknown type");
+                }
+            case PROPERTY_SUBGRAPH:
+                InputGraph graph = parseGraph("");
+                new Group(null).addElement(graph);
+                return graph;
+            default:
+                throw new IOException("Unknown type");
+        }
+    }
+
+    @Override
+    public GraphDocument parse() throws IOException {
+        folderStack.push(rootDocument);
+        hashStack.push(null);
+        if (monitor != null) {
+            monitor.setState("Starting parsing");
+        }
+        try {
+            while(true) {
+                parseRoot();
+            }
+        } catch (EOFException e) {
+
+        }
+        if (monitor != null) {
+            monitor.setState("Finished parsing");
+        }
+        return rootDocument;
+    }
+
+    private void parseRoot() throws IOException {
+        int type = readByte();
+        switch(type) {
+            case BEGIN_GRAPH: {
+                final Folder parent = folderStack.peek();
+                final InputGraph graph = parseGraph();
+                SwingUtilities.invokeLater(new Runnable(){
+                    @Override
+                    public void run() {
+                        parent.addElement(graph);
+                    }
+                });
+                break;
+            }
+            case BEGIN_GROUP: {
+                final Folder parent = folderStack.peek();
+                final Group group = parseGroup(parent);
+                if (callback == null || parent instanceof Group) {
+                    SwingUtilities.invokeLater(new Runnable(){
+                        @Override
+                        public void run() {
+                            parent.addElement(group);
+                        }
+                    });
+                }
+                folderStack.push(group);
+                hashStack.push(null);
+                if (callback != null && parent instanceof GraphDocument) {
+                    callback.started(group);
+                }
+                break;
+            }
+            case CLOSE_GROUP: {
+                if (folderStack.isEmpty()) {
+                    throw new IOException("Unbalanced groups");
+                }
+                folderStack.pop();
+                hashStack.pop();
+                break;
+            }
+            default:
+                throw new IOException("unknown root : " + type);
+        }
+    }
+
+    private Group parseGroup(Folder parent) throws IOException {
+        String name = readPoolObject(String.class);
+        String shortName = readPoolObject(String.class);
+        if (monitor != null) {
+            monitor.setState(shortName);
+        }
+        Method method = readPoolObject(Method.class);
+        int bci = readInt();
+        Group group = new Group(parent);
+        group.getProperties().setProperty("name", name);
+        if (method != null) {
+            InputMethod inMethod = new InputMethod(group, method.name, shortName, bci);
+            inMethod.setBytecodes("TODO");
+            group.setMethod(inMethod);
+        }
+        return group;
+    }
+
+    private InputGraph parseGraph() throws IOException {
+        if (monitor != null) {
+            monitor.updateProgress();
+        }
+        String title = readPoolObject(String.class);
+        digest.reset();
+        InputGraph graph = parseGraph(title);
+        byte[] d = digest.digest();
+        byte[] hash = hashStack.peek();
+        if (hash != null && Arrays.equals(hash, d)) {
+            graph.getProperties().setProperty("_isDuplicate", "true");
+        } else {
+            hashStack.pop();
+            hashStack.push(d);
+        }
+        return graph;
+    }
+
+    private InputGraph parseGraph(String title) throws IOException {
+        InputGraph graph = new InputGraph(title);
+        parseNodes(graph);
+        parseBlocks(graph);
+        graph.ensureNodesInBlocks();
+        return graph;
+    }
+
+    private void parseBlocks(InputGraph graph) throws IOException {
+        int blockCount = readInt();
+        List<Edge> edges = new LinkedList<>();
+        for (int i = 0; i < blockCount; i++) {
+            int id = readInt();
+            String name = id >= 0 ? Integer.toString(id) : NO_BLOCK;
+            InputBlock block = graph.addBlock(name);
+            int nodeCount = readInt();
+            for (int j = 0; j < nodeCount; j++) {
+                int nodeId = readInt();
+                if (nodeId < 0) {
+                    continue;
+                }
+                final Properties properties = graph.getNode(nodeId).getProperties();
+                final String oldBlock = properties.get("block");
+                if(oldBlock != null) {
+                    properties.setProperty("block", oldBlock + ", " + name);
+                } else {
+                    block.addNode(nodeId);
+                    properties.setProperty("block", name);
+                }
+            }
+            int edgeCount = readInt();
+            for (int j = 0; j < edgeCount; j++) {
+                int to = readInt();
+                edges.add(new Edge(id, to));
+            }
+        }
+        for (Edge e : edges) {
+            String fromName = e.from >= 0 ? Integer.toString(e.from) : NO_BLOCK;
+            String toName = e.to >= 0 ? Integer.toString(e.to) : NO_BLOCK;
+            graph.addBlockEdge(graph.getBlock(fromName), graph.getBlock(toName));
+        }
+    }
+
+    private void parseNodes(InputGraph graph) throws IOException {
+        int count = readInt();
+        Map<String, Object> props = new HashMap<>();
+        List<Edge> inputEdges = new ArrayList<>(count);
+        List<Edge> succEdges = new ArrayList<>(count);
+        for (int i = 0; i < count; i++) {
+            int id = readInt();
+            InputNode node = new InputNode(id);
+            final Properties properties = node.getProperties();
+            NodeClass nodeClass = readPoolObject(NodeClass.class);
+            int preds = readByte();
+            if (preds > 0) {
+                properties.setProperty("hasPredecessor", "true");
+            }
+            properties.setProperty("idx", Integer.toString(id));
+            int propCount = readShort();
+            for (int j = 0; j < propCount; j++) {
+                String key = readPoolObject(String.class);
+                if (key.equals("hasPredecessor") || key.equals("name") || key.equals("class") || key.equals("id") || key.equals("idx")) {
+                    key = "!data." + key;
+                }
+                Object value = readPropertyObject();
+                if (value instanceof InputGraph) {
+                    InputGraph subgraph = (InputGraph) value;
+                    subgraph.getProperties().setProperty("name", node.getId() + ":" + key);
+                    node.addSubgraph((InputGraph) value);
+                } else {
+                    properties.setProperty(key, value != null ? value.toString() : "null");
+                    props.put(key, value);
+                }
+            }
+            ArrayList<Edge> currentEdges = new ArrayList<>();
+            int portNum = 0;
+            for (TypedPort p : nodeClass.inputs) {
+                if (p.isList) {
+                    int size = readShort();
+                    for (int j = 0; j < size; j++) {
+                        int in = readInt();
+                        if (in >= 0) {
+                            Edge e = new Edge(in, id, (char) (preds + portNum), p.name + "[" + j + "]", p.type.toString(Length.S), true);
+                            currentEdges.add(e);
+                            inputEdges.add(e);
+                            portNum++;
+                        }
+                    }
+                } else {
+                    int in = readInt();
+                    if (in >= 0) {
+                        Edge e = new Edge(in, id, (char) (preds + portNum), p.name, p.type.toString(Length.S), true);
+                        currentEdges.add(e);
+                        inputEdges.add(e);
+                        portNum++;
+                    }
+                }
+
+            }
+            portNum = 0;
+            for (Port p : nodeClass.sux) {
+                if (p.isList) {
+                    int size = readShort();
+                    for (int j = 0; j < size; j++) {
+                        int sux = readInt();
+                        if (sux >= 0) {
+                            Edge e = new Edge(id, sux, (char) portNum, p.name + "[" + j + "]", "Successor", false);
+                            currentEdges.add(e);
+                            succEdges.add(e);
+                            portNum++;
+                        }
+                    }
+                } else {
+                    int sux = readInt();
+                    if (sux >= 0) {
+                        Edge e = new Edge(id, sux, (char) portNum, p.name, "Successor", false);
+                        currentEdges.add(e);
+                        succEdges.add(e);
+                        portNum++;
+                    }
+                }
+            }
+            properties.setProperty("name", createName(currentEdges, props, nodeClass.nameTemplate));
+            properties.setProperty("class", nodeClass.className);
+            switch (nodeClass.className) {
+                case "BeginNode":
+                    properties.setProperty("shortName", "B");
+                    break;
+                case "EndNode":
+                    properties.setProperty("shortName", "E");
+                    break;
+            }
+            graph.addNode(node);
+            props.clear();
+        }
+
+        Set<InputNode> nodesWithSuccessor = new HashSet<>();
+
+        for (Edge e : succEdges) {
+            assert !e.input;
+            char fromIndex = e.num;
+            nodesWithSuccessor.add(graph.getNode(e.from));
+            char toIndex = 0;
+            graph.addEdge(InputEdge.createImmutable(fromIndex, toIndex, e.from, e.to, e.label, e.type));
+        }
+        for (Edge e : inputEdges) {
+            assert e.input;
+            char fromIndex = (char) (nodesWithSuccessor.contains(graph.getNode(e.from)) ? 1 : 0);
+            char toIndex = e.num;
+            graph.addEdge(InputEdge.createImmutable(fromIndex, toIndex, e.from, e.to, e.label, e.type));
+        }
+    }
+
+    private String createName(List<Edge> edges, Map<String, Object> properties, String template) {
+        Pattern p = Pattern.compile("\\{(p|i)#([a-zA-Z0-9$_]+)(/(l|m|s))?\\}");
+        Matcher m = p.matcher(template);
+        StringBuffer sb = new StringBuffer();
+        while (m.find()) {
+            String name = m.group(2);
+            String type = m.group(1);
+            String result;
+            switch (type) {
+                case "i":
+                    StringBuilder inputString = new StringBuilder();
+                    for(Edge edge : edges) {
+                        if (edge.label.startsWith(name) && (name.length() == edge.label.length() || edge.label.charAt(name.length()) == '[')) {
+                            if (inputString.length() > 0) {
+                                inputString.append(", ");
+                            }
+                            inputString.append(edge.from);
+                        }
+                    }
+                    result = inputString.toString();
+                    break;
+                case "p":
+                    Object prop = properties.get(name);
+                    String length = m.group(4);
+                    if (prop == null) {
+                        result = "?";
+                    } else if (length != null && prop instanceof LengthToString) {
+                        LengthToString lengthProp = (LengthToString) prop;
+                        switch(length) {
+                            default:
+                            case "l":
+                                result = lengthProp.toString(Length.L);
+                                break;
+                            case "m":
+                                result = lengthProp.toString(Length.M);
+                                break;
+                            case "s":
+                                result = lengthProp.toString(Length.S);
+                                break;
+                        }
+                    } else {
+                        result = prop.toString();
+                    }
+                    break;
+                default:
+                    result = "#?#";
+                    break;
+            }
+            result = result.replace("\\", "\\\\");
+            result = result.replace("$", "\\$");
+            m.appendReplacement(sb, result);
+        }
+        m.appendTail(sb);
+        return sb.toString().intern();
+    }
+
+    private static class Edge {
+        final int from;
+        final int to;
+        final char num;
+        final String label;
+        final String type;
+        final boolean input;
+        public Edge(int from, int to) {
+            this(from, to, (char) 0, null, null, false);
+        }
+        public Edge(int from, int to, char num, String label, String type, boolean input) {
+            this.from = from;
+            this.to = to;
+            this.label = label != null ? label.intern() : label;
+            this.type = type != null ? type.intern() : type;
+            this.num = num;
+            this.input = input;
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/serialization/GraphParser.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,32 @@
+/*
+ * 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.
+ */
+package com.sun.hotspot.igv.data.serialization;
+
+import com.sun.hotspot.igv.data.GraphDocument;
+import java.io.IOException;
+
+public interface GraphParser {
+    public GraphDocument parse() throws IOException;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/serialization/ParseMonitor.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,33 @@
+/*
+ * 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.
+ */
+package com.sun.hotspot.igv.data.serialization;
+
+public interface ParseMonitor {
+
+    public void updateProgress();
+
+    public void setState(String state);
+
+}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/serialization/Parser.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/serialization/Parser.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,31 +23,34 @@
  */
 package com.sun.hotspot.igv.data.serialization;
 
-import com.sun.hotspot.igv.data.GraphDocument;
-import com.sun.hotspot.igv.data.Group;
-import com.sun.hotspot.igv.data.InputBlock;
-import com.sun.hotspot.igv.data.InputEdge;
-import com.sun.hotspot.igv.data.InputGraph;
-import com.sun.hotspot.igv.data.InputMethod;
-import com.sun.hotspot.igv.data.InputNode;
-import com.sun.hotspot.igv.data.Properties;
-import com.sun.hotspot.igv.data.Property;
-import com.sun.hotspot.igv.data.services.GroupCallback;
+import com.sun.hotspot.igv.data.*;
 import com.sun.hotspot.igv.data.serialization.XMLParser.ElementHandler;
 import com.sun.hotspot.igv.data.serialization.XMLParser.HandoverElementHandler;
-import com.sun.hotspot.igv.data.serialization.XMLParser.ParseMonitor;
 import com.sun.hotspot.igv.data.serialization.XMLParser.TopElementHandler;
+import com.sun.hotspot.igv.data.services.GroupCallback;
 import java.io.IOException;
+import java.io.InputStream;
+import java.nio.channels.Channels;
+import java.nio.channels.ReadableByteChannel;
+import java.util.ArrayList;
 import java.util.HashMap;
+import java.util.Map;
+import javax.swing.SwingUtilities;
+import javax.xml.parsers.ParserConfigurationException;
+import javax.xml.parsers.SAXParserFactory;
+import javax.xml.transform.Source;
+import javax.xml.transform.stream.StreamSource;
+import javax.xml.validation.SchemaFactory;
 import org.xml.sax.InputSource;
 import org.xml.sax.SAXException;
+import org.xml.sax.SAXParseException;
 import org.xml.sax.XMLReader;
 
 /**
  *
  * @author Thomas Wuerthinger
  */
-public class Parser {
+public class Parser implements GraphParser {
 
     public static final String INDENT = "  ";
     public static final String TOP_ELEMENT = "graphDocument";
@@ -63,6 +66,7 @@
     public static final String REMOVE_EDGE_ELEMENT = "removeEdge";
     public static final String REMOVE_NODE_ELEMENT = "removeNode";
     public static final String METHOD_NAME_PROPERTY = "name";
+    public static final String GROUP_NAME_PROPERTY = "name";
     public static final String METHOD_IS_PUBLIC_PROPERTY = "public";
     public static final String METHOD_IS_STATIC_PROPERTY = "static";
     public static final String TRUE_VALUE = "true";
@@ -71,9 +75,13 @@
     public static final String NODE_ID_PROPERTY = "id";
     public static final String FROM_PROPERTY = "from";
     public static final String TO_PROPERTY = "to";
+    public static final String TYPE_PROPERTY = "type";
     public static final String PROPERTY_NAME_PROPERTY = "name";
     public static final String GRAPH_NAME_PROPERTY = "name";
-    public static final String TO_INDEX_PROPERTY = "index";
+    public static final String FROM_INDEX_PROPERTY = "fromIndex";
+    public static final String TO_INDEX_PROPERTY = "toIndex";
+    public static final String TO_INDEX_ALT_PROPERTY = "index";
+    public static final String LABEL_PROPERTY = "label";
     public static final String METHOD_ELEMENT = "method";
     public static final String INLINE_ELEMENT = "inline";
     public static final String BYTECODES_ELEMENT = "bytecodes";
@@ -86,13 +94,23 @@
     public static final String SUCCESSOR_ELEMENT = "successor";
     public static final String ASSEMBLY_ELEMENT = "assembly";
     public static final String DIFFERENCE_PROPERTY = "difference";
-    private TopElementHandler xmlDocument = new TopElementHandler();
-    private boolean difference;
+    private TopElementHandler<GraphDocument> xmlDocument = new TopElementHandler<>();
+    private Map<Group, Boolean> differenceEncoding = new HashMap<>();
+    private Map<Group, InputGraph> lastParsedGraph = new HashMap<>();
     private GroupCallback groupCallback;
-    private HashMap<String, Integer> idCache = new HashMap<String, Integer>();
+    private HashMap<String, Integer> idCache = new HashMap<>();
+    private ArrayList<Pair<String, String>> blockConnections = new ArrayList<>();
     private int maxId = 0;
+    private GraphDocument graphDocument;
+    private final ParseMonitor monitor;
+    private final ReadableByteChannel channel;
 
     private int lookupID(String i) {
+        try {
+            return Integer.parseInt(i);
+        } catch (NumberFormatException nfe) {
+            // ignore
+        }
         Integer id = idCache.get(i);
         if (id == null) {
             id = maxId++;
@@ -106,41 +124,40 @@
 
         @Override
         protected GraphDocument start() throws SAXException {
-            return new GraphDocument();
+            graphDocument = new GraphDocument();
+            return graphDocument;
         }
     };
     // <group>
-    private ElementHandler<Group, GraphDocument> groupHandler = new XMLParser.ElementHandler<Group, GraphDocument>(GROUP_ELEMENT) {
+    private ElementHandler<Group, Folder> groupHandler = new XMLParser.ElementHandler<Group, Folder>(GROUP_ELEMENT) {
 
         @Override
         protected Group start() throws SAXException {
-            Group group = new Group();
-            Parser.this.difference = false;
+            final Group group = new Group(this.getParentObject());
+
             String differenceProperty = this.readAttribute(DIFFERENCE_PROPERTY);
-            if (differenceProperty != null && (differenceProperty.equals("1") || differenceProperty.equals("true"))) {
-                Parser.this.difference = true;
-            }
+            Parser.this.differenceEncoding.put(group, (differenceProperty != null && (differenceProperty.equals("1") || differenceProperty.equals("true"))));
 
             ParseMonitor monitor = getMonitor();
             if (monitor != null) {
                 monitor.setState(group.getName());
             }
 
+            final Folder parent = getParentObject();
+            if (groupCallback == null || parent instanceof Group) {
+                SwingUtilities.invokeLater(new Runnable(){
+                    @Override
+                    public void run() {
+                        parent.addElement(group);
+                    }
+                });
+            }
+
             return group;
         }
 
         @Override
         protected void end(String text) throws SAXException {
-            if (groupCallback == null) {
-                getParentObject().addGroup(getObject());
-            }
-        }
-    };
-    private HandoverElementHandler<Group> assemblyHandler = new XMLParser.HandoverElementHandler<Group>(ASSEMBLY_ELEMENT, true) {
-
-        @Override
-        protected void end(String text) throws SAXException {
-            getParentObject().setAssembly(text);
         }
     };
     // <method>
@@ -155,7 +172,7 @@
         }
     };
 
-    private InputMethod parseMethod(XMLParser.ElementHandler handler, Group group) throws SAXException {
+    private InputMethod parseMethod(XMLParser.ElementHandler<?,?> handler, Group group) throws SAXException {
         String s = handler.readRequiredAttribute(METHOD_BCI_PROPERTY);
         int bci = 0;
         try {
@@ -175,7 +192,7 @@
         }
     };
     // <inlined>
-    private HandoverElementHandler<InputMethod> inlinedHandler = new XMLParser.HandoverElementHandler<InputMethod>(INLINE_ELEMENT);
+    private HandoverElementHandler<InputMethod> inlinedHandler = new XMLParser.HandoverElementHandler<>(INLINE_ELEMENT);
     // <inlined><method>
     private ElementHandler<InputMethod, InputMethod> inlinedMethodHandler = new XMLParser.ElementHandler<InputMethod, InputMethod>(METHOD_ELEMENT) {
 
@@ -189,45 +206,110 @@
     // <graph>
     private ElementHandler<InputGraph, Group> graphHandler = new XMLParser.ElementHandler<InputGraph, Group>(GRAPH_ELEMENT) {
 
-        private InputGraph graph;
-
         @Override
         protected InputGraph start() throws SAXException {
-
             String name = readAttribute(GRAPH_NAME_PROPERTY);
-            InputGraph previous = getParentObject().getLastAdded();
-            if (!difference) {
-                previous = null;
+            InputGraph curGraph = new InputGraph(name);
+            if (differenceEncoding.get(getParentObject())) {
+                InputGraph previous = lastParsedGraph.get(getParentObject());
+                lastParsedGraph.put(getParentObject(), curGraph);
+                if (previous != null) {
+                    for (InputNode n : previous.getNodes()) {
+                        curGraph.addNode(n);
+                    }
+                    for (InputEdge e : previous.getEdges()) {
+                        curGraph.addEdge(e);
+                    }
+                }
             }
-            InputGraph curGraph = new InputGraph(getParentObject(), previous, name);
-            this.graph = curGraph;
+            ParseMonitor monitor = getMonitor();
+            if (monitor != null) {
+                monitor.updateProgress();
+            }
             return curGraph;
         }
 
         @Override
         protected void end(String text) throws SAXException {
-            getParentObject().addGraph(graph);
-            graph.resolveBlockLinks();
+            // NOTE: Some graphs intentionally don't provide blocks. Instead
+            //       they later generate the blocks from other information such
+            //       as node properties (example: ServerCompilerScheduler).
+            //       Thus, we shouldn't assign nodes that don't belong to any
+            //       block to some artificial block below unless blocks are
+            //       defined and nodes are assigned to them.
+
+            final InputGraph graph = getObject();
+            final Group parent = getParentObject();
+            if (graph.getBlocks().size() > 0) {
+                boolean blocksContainNodes = false;
+                for (InputBlock b : graph.getBlocks()) {
+                    if (b.getNodes().size() > 0) {
+                        blocksContainNodes = true;
+                        break;
+                    }
+                }
+
+                if (!blocksContainNodes) {
+                    graph.clearBlocks();
+                    blockConnections.clear();
+                } else {
+                    // Blocks and their nodes defined: add other nodes to an
+                    //  artificial "no block" block
+                    InputBlock noBlock = null;
+                    for (InputNode n : graph.getNodes()) {
+                        if (graph.getBlock(n) == null) {
+                            if (noBlock == null) {
+                                noBlock = graph.addBlock("(no block)");
+                            }
+
+                            noBlock.addNode(n.getId());
+                        }
+
+                        assert graph.getBlock(n) != null;
+                    }
+                }
+            }
+
+            // Resolve block successors
+            for (Pair<String, String> p : blockConnections) {
+                final InputBlock left = graph.getBlock(p.getLeft());
+                assert left != null;
+                final InputBlock right = graph.getBlock(p.getRight());
+                assert right != null;
+                graph.addBlockEdge(left, right);
+            }
+            blockConnections.clear();
+
+            SwingUtilities.invokeLater(new Runnable(){
+
+                @Override
+                public void run() {
+                    // Add to group
+                    parent.addElement(graph);
+                }
+            });
         }
     };
     // <nodes>
-    private HandoverElementHandler<InputGraph> nodesHandler = new HandoverElementHandler<InputGraph>(NODES_ELEMENT);
+    private HandoverElementHandler<InputGraph> nodesHandler = new HandoverElementHandler<>(NODES_ELEMENT);
     // <controlFlow>
-    private HandoverElementHandler<InputGraph> controlFlowHandler = new HandoverElementHandler<InputGraph>(CONTROL_FLOW_ELEMENT);
+    private HandoverElementHandler<InputGraph> controlFlowHandler = new HandoverElementHandler<>(CONTROL_FLOW_ELEMENT);
     // <block>
     private ElementHandler<InputBlock, InputGraph> blockHandler = new ElementHandler<InputBlock, InputGraph>(BLOCK_ELEMENT) {
 
         @Override
         protected InputBlock start() throws SAXException {
             InputGraph graph = getParentObject();
-            String name = readRequiredAttribute(BLOCK_NAME_PROPERTY).intern();
-            InputBlock b = new InputBlock(getParentObject(), name);
-            graph.addBlock(b);
+            String name = readRequiredAttribute(BLOCK_NAME_PROPERTY);
+            InputBlock b = graph.addBlock(name);
+            for (InputNode n : b.getNodes()) {
+                assert graph.getBlock(n).equals(b);
+            }
             return b;
         }
     };
     // <nodes>
-    private HandoverElementHandler<InputBlock> blockNodesHandler = new HandoverElementHandler<InputBlock>(NODES_ELEMENT);
+    private HandoverElementHandler<InputBlock> blockNodesHandler = new HandoverElementHandler<>(NODES_ELEMENT);
     // <node>
     private ElementHandler<InputBlock, InputBlock> blockNodeHandler = new ElementHandler<InputBlock, InputBlock>(NODE_ELEMENT) {
 
@@ -246,14 +328,14 @@
         }
     };
     // <successors>
-    private HandoverElementHandler<InputBlock> successorsHandler = new HandoverElementHandler<InputBlock>(SUCCESSORS_ELEMENT);
+    private HandoverElementHandler<InputBlock> successorsHandler = new HandoverElementHandler<>(SUCCESSORS_ELEMENT);
     // <successor>
     private ElementHandler<InputBlock, InputBlock> successorHandler = new ElementHandler<InputBlock, InputBlock>(SUCCESSOR_ELEMENT) {
 
         @Override
         protected InputBlock start() throws SAXException {
             String name = readRequiredAttribute(BLOCK_NAME_PROPERTY);
-            getParentObject().addSuccessor(name);
+            blockConnections.add(new Pair<>(getParentObject().getName(), name));
             return getParentObject();
         }
     };
@@ -290,7 +372,7 @@
         }
     };
     // <graph>
-    private HandoverElementHandler<InputGraph> edgesHandler = new HandoverElementHandler<InputGraph>(EDGES_ELEMENT);
+    private HandoverElementHandler<InputGraph> edgesHandler = new HandoverElementHandler<>(EDGES_ELEMENT);
 
     // Local class for edge elements
     private class EdgeElementHandler extends ElementHandler<InputEdge, InputGraph> {
@@ -301,24 +383,37 @@
 
         @Override
         protected InputEdge start() throws SAXException {
+            int fromIndex = 0;
             int toIndex = 0;
             int from = -1;
             int to = -1;
+            String label = null;
+            String type = null;
 
             try {
+                String fromIndexString = readAttribute(FROM_INDEX_PROPERTY);
+                if (fromIndexString != null) {
+                    fromIndex = Integer.parseInt(fromIndexString);
+                }
+
                 String toIndexString = readAttribute(TO_INDEX_PROPERTY);
+                if (toIndexString == null) {
+                    toIndexString = readAttribute(TO_INDEX_ALT_PROPERTY);
+                }
                 if (toIndexString != null) {
                     toIndex = Integer.parseInt(toIndexString);
                 }
 
+                label = readAttribute(LABEL_PROPERTY);
+                type = readAttribute(TYPE_PROPERTY);
+
                 from = lookupID(readRequiredAttribute(FROM_PROPERTY));
                 to = lookupID(readRequiredAttribute(TO_PROPERTY));
             } catch (NumberFormatException e) {
                 throw new SAXException(e);
             }
 
-
-            InputEdge conn = new InputEdge((char) toIndex, from, to);
+            InputEdge conn = new InputEdge((char) fromIndex, (char) toIndex, from, to, label, type == null ? "" : type);
             return start(conn);
         }
 
@@ -345,14 +440,20 @@
         }
     };
     // <properties>
-    private HandoverElementHandler<Properties.Provider> propertiesHandler = new HandoverElementHandler<Properties.Provider>(PROPERTIES_ELEMENT);
+    private HandoverElementHandler<Properties.Provider> propertiesHandler = new HandoverElementHandler<>(PROPERTIES_ELEMENT);
     // <properties>
     private HandoverElementHandler<Group> groupPropertiesHandler = new HandoverElementHandler<Group>(PROPERTIES_ELEMENT) {
 
         @Override
         public void end(String text) throws SAXException {
-            if (groupCallback != null) {
-                groupCallback.started(getParentObject());
+            if (groupCallback != null && getParentObject().getParent() instanceof GraphDocument) {
+                final Group group = getParentObject();
+                SwingUtilities.invokeLater(new Runnable() {
+                    @Override
+                    public void run() {
+                        groupCallback.started(group);
+                    }
+                });
             }
         }
     };
@@ -361,30 +462,32 @@
 
         @Override
         public String start() throws SAXException {
-            return readRequiredAttribute(PROPERTY_NAME_PROPERTY).intern();
-        }
+            return readRequiredAttribute(PROPERTY_NAME_PROPERTY);
+         }
 
         @Override
         public void end(String text) {
-            getParentObject().getProperties().setProperty(getObject(), text.trim().intern());
+            getParentObject().getProperties().setProperty(getObject(), text.trim());
         }
     };
 
-    public Parser() {
-        this(null);
+    public Parser(ReadableByteChannel channel) {
+        this(channel, null, null);
     }
 
-    public Parser(GroupCallback groupCallback) {
+    public Parser(ReadableByteChannel channel, ParseMonitor monitor, GroupCallback groupCallback) {
 
         this.groupCallback = groupCallback;
+        this.monitor = monitor;
+        this.channel = channel;
 
         // Initialize dependencies
         xmlDocument.addChild(topHandler);
         topHandler.addChild(groupHandler);
 
         groupHandler.addChild(methodHandler);
-        groupHandler.addChild(assemblyHandler);
         groupHandler.addChild(graphHandler);
+        groupHandler.addChild(groupHandler);
 
         methodHandler.addChild(inlinedHandler);
         methodHandler.addChild(bytecodesHandler);
@@ -420,14 +523,40 @@
     }
 
     // Returns a new GraphDocument object deserialized from an XML input source.
-    public GraphDocument parse(XMLReader reader, InputSource source, XMLParser.ParseMonitor monitor) throws SAXException {
-        reader.setContentHandler(new XMLParser(xmlDocument, monitor));
+    @Override
+    public GraphDocument parse() throws IOException {
+        if (monitor != null) {
+            monitor.setState("Starting parsing");
+        }
         try {
-            reader.parse(source);
-        } catch (IOException ex) {
+            XMLReader reader = createReader();
+            reader.setContentHandler(new XMLParser(xmlDocument, monitor));
+            reader.parse(new InputSource(Channels.newInputStream(channel)));
+        } catch (SAXException ex) {
+            if (!(ex instanceof SAXParseException) || !"XML document structures must start and end within the same entity.".equals(ex.getMessage())) {
+                throw new IOException(ex);
+            }
+        }
+        if (monitor != null) {
+            monitor.setState("Finished parsing");
+        }
+        return graphDocument;
+    }
+
+    private XMLReader createReader() throws SAXException {
+        try {
+            SAXParserFactory pfactory = SAXParserFactory.newInstance();
+            pfactory.setValidating(true);
+            pfactory.setNamespaceAware(true);
+
+            // Enable schema validation
+            SchemaFactory sfactory = SchemaFactory.newInstance("http://www.w3.org/2001/XMLSchema");
+            InputStream stream = Parser.class.getResourceAsStream("graphdocument.xsd");
+            pfactory.setSchema(sfactory.newSchema(new Source[]{new StreamSource(stream)}));
+
+            return pfactory.newSAXParser().getXMLReader();
+        } catch (ParserConfigurationException ex) {
             throw new SAXException(ex);
         }
-
-        return topHandler.getObject();
     }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/serialization/Printer.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/serialization/Printer.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,17 +23,9 @@
  */
 package com.sun.hotspot.igv.data.serialization;
 
-import com.sun.hotspot.igv.data.GraphDocument;
-import com.sun.hotspot.igv.data.Group;
-import com.sun.hotspot.igv.data.InputBlock;
-import com.sun.hotspot.igv.data.InputBytecode;
-import com.sun.hotspot.igv.data.InputEdge;
-import com.sun.hotspot.igv.data.InputGraph;
-import com.sun.hotspot.igv.data.InputMethod;
-import com.sun.hotspot.igv.data.InputNode;
-import com.sun.hotspot.igv.data.Properties;
-import com.sun.hotspot.igv.data.Property;
+import com.sun.hotspot.igv.data.*;
 import java.io.IOException;
+import java.io.InputStream;
 import java.io.Writer;
 import java.util.HashSet;
 import java.util.Set;
@@ -44,6 +36,16 @@
  */
 public class Printer {
 
+    private InputStream in;
+
+    public Printer() {
+        this(null);
+    }
+
+    public Printer(InputStream inputStream) {
+        this.in = inputStream;
+    }
+
     public void export(Writer writer, GraphDocument document) {
 
         XMLWriter xmlWriter = new XMLWriter(writer);
@@ -57,8 +59,12 @@
     private void export(XMLWriter xmlWriter, GraphDocument document) throws IOException {
         xmlWriter.startTag(Parser.ROOT_ELEMENT);
         xmlWriter.writeProperties(document.getProperties());
-        for (Group g : document.getGroups()) {
-            export(xmlWriter, g);
+        for (FolderElement e : document.getElements()) {
+            if (e instanceof Group) {
+                export(xmlWriter, (Group) e);
+            } else if (e instanceof InputGraph) {
+                export(xmlWriter, (InputGraph)e, null, false);
+            }
         }
 
         xmlWriter.endTag();
@@ -71,14 +77,29 @@
         writer.startTag(Parser.GROUP_ELEMENT, attributes);
         writer.writeProperties(g.getProperties());
 
-        if (g.getMethod() != null) {
-            export(writer, g.getMethod());
+        boolean shouldExport = true;
+        if (in != null) {
+            char c = (char) in.read();
+            if (c != 'y') {
+                shouldExport = false;
+            }
         }
 
-        InputGraph previous = null;
-        for (InputGraph graph : g.getGraphs()) {
-            export(writer, graph, previous, true);
-            previous = graph;
+        if (shouldExport) {
+            if (g.getMethod() != null) {
+                export(writer, g.getMethod());
+            }
+
+            InputGraph previous = null;
+            for (FolderElement e : g.getElements()) {
+                if (e instanceof InputGraph) {
+                    InputGraph graph = (InputGraph) e;
+                    export(writer, graph, previous, true);
+                    previous = graph;
+                } else if (e instanceof Group) {
+                    export(writer, (Group) e);
+                }
+            }
         }
 
         writer.endTag();
@@ -90,8 +111,8 @@
         writer.writeProperties(graph.getProperties());
         writer.startTag(Parser.NODES_ELEMENT);
 
-        Set<InputNode> removed = new HashSet<InputNode>();
-        Set<InputNode> equal = new HashSet<InputNode>();
+        Set<InputNode> removed = new HashSet<>();
+        Set<InputNode> equal = new HashSet<>();
 
         if (previous != null) {
             for (InputNode n : previous.getNodes()) {
@@ -122,8 +143,8 @@
         writer.endTag();
 
         writer.startTag(Parser.EDGES_ELEMENT);
-        Set<InputEdge> removedEdges = new HashSet<InputEdge>();
-        Set<InputEdge> equalEdges = new HashSet<InputEdge>();
+        Set<InputEdge> removedEdges = new HashSet<>();
+        Set<InputEdge> equalEdges = new HashSet<>();
 
         if (previous != null) {
             for (InputEdge e : previous.getEdges()) {
@@ -153,23 +174,25 @@
 
         writer.startTag(Parser.CONTROL_FLOW_ELEMENT);
         for (InputBlock b : graph.getBlocks()) {
-
             writer.startTag(Parser.BLOCK_ELEMENT, new Properties(Parser.BLOCK_NAME_PROPERTY, b.getName()));
 
-            writer.startTag(Parser.SUCCESSORS_ELEMENT);
-            for (InputBlock s : b.getSuccessors()) {
-                writer.simpleTag(Parser.SUCCESSOR_ELEMENT, new Properties(Parser.BLOCK_NAME_PROPERTY, s.getName()));
+            if (b.getSuccessors().size() > 0) {
+                writer.startTag(Parser.SUCCESSORS_ELEMENT);
+                for (InputBlock s : b.getSuccessors()) {
+                    writer.simpleTag(Parser.SUCCESSOR_ELEMENT, new Properties(Parser.BLOCK_NAME_PROPERTY, s.getName()));
+                }
+                writer.endTag();
             }
-            writer.endTag();
 
+            if (b.getNodes().size() > 0) {
             writer.startTag(Parser.NODES_ELEMENT);
-            for (InputNode n : b.getNodes()) {
-                writer.simpleTag(Parser.NODE_ELEMENT, new Properties(Parser.NODE_ID_PROPERTY, n.getId() + ""));
+                for (InputNode n : b.getNodes()) {
+                    writer.simpleTag(Parser.NODE_ELEMENT, new Properties(Parser.NODE_ID_PROPERTY, n.getId() + ""));
+                }
+                writer.endTag();
             }
-            writer.endTag();
 
             writer.endTag();
-
         }
 
         writer.endTag();
@@ -199,8 +222,8 @@
             b.append(" ");
             b.append(code.getName());
             b.append("\n");
+        }
 
-        }
         b.append("]]>");
         w.write(b.toString());
         w.endTag();
@@ -209,9 +232,15 @@
 
     private Properties createProperties(InputEdge edge) {
         Properties p = new Properties();
-        p.setProperty(Parser.TO_INDEX_PROPERTY, Integer.toString(edge.getToIndex()));
+        if (edge.getToIndex() != 0) {
+            p.setProperty(Parser.TO_INDEX_PROPERTY, Integer.toString(edge.getToIndex()));
+        }
+        if (edge.getFromIndex() != 0) {
+            p.setProperty(Parser.FROM_INDEX_PROPERTY, Integer.toString(edge.getFromIndex()));
+        }
         p.setProperty(Parser.TO_PROPERTY, Integer.toString(edge.getTo()));
         p.setProperty(Parser.FROM_PROPERTY, Integer.toString(edge.getFrom()));
+        p.setProperty(Parser.TYPE_PROPERTY, edge.getType());
         return p;
     }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/serialization/XMLParser.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/serialization/XMLParser.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,7 +23,6 @@
  */
 package com.sun.hotspot.igv.data.serialization;
 
-import com.sun.hotspot.igv.data.Property;
 import com.sun.hotspot.igv.data.Properties;
 import java.util.HashMap;
 import java.util.Stack;
@@ -38,13 +37,6 @@
  */
 public class XMLParser implements ContentHandler {
 
-    public static interface ParseMonitor {
-
-        public void setProgress(double d);
-
-        public void setState(String state);
-    }
-
     public static class MissingAttributeException extends SAXException {
 
         private String name;
@@ -85,24 +77,25 @@
     public static class ElementHandler<T, P> {
 
         private String name;
-        private T object;
+        private Stack<T> object = new Stack<>();
         private Attributes attr;
         private StringBuilder currentText;
         private ParseMonitor monitor;
         private HashMap<String, ElementHandler<?, ? super T>> hashtable;
         private boolean needsText;
-        private ElementHandler<P, ?> parentElement;
+        private Stack<ElementHandler<P, ?>> parentElement = new Stack<>();
+        private Stack<P> parentObject = new Stack<>();
 
         public ElementHandler(String name) {
             this(name, false);
         }
 
         public ElementHandler<P, ?> getParentElement() {
-            return parentElement;
+            return parentElement.peek();
         }
 
         public P getParentObject() {
-            return getParentElement().getObject();
+            return parentObject.peek();
         }
 
         protected boolean needsText() {
@@ -110,7 +103,7 @@
         }
 
         public ElementHandler(String name, boolean needsText) {
-            this.hashtable = new HashMap<String, ElementHandler<?, ? super T>>();
+            this.hashtable = new HashMap<>();
             this.name = name;
             this.needsText = needsText;
         }
@@ -133,7 +126,7 @@
         }
 
         public T getObject() {
-            return object;
+            return object.size() == 0 ? null : object.peek();
         }
 
         public String readAttribute(String name) {
@@ -151,8 +144,8 @@
         public void processAttributesAsProperties(Properties p) {
             int length = attr.getLength();
             for (int i = 0; i < length; i++) {
-                String val = attr.getValue(i).intern();
-                String localName = attr.getLocalName(i).intern();
+                String val = attr.getValue(i);
+                String localName = attr.getLocalName(i);
                 p.setProperty(val, localName);
             }
         }
@@ -161,8 +154,9 @@
             this.currentText = new StringBuilder();
             this.attr = attr;
             this.monitor = monitor;
-            this.parentElement = parentElement;
-            object = start();
+            this.parentElement.push(parentElement);
+            parentObject.push(parentElement.getObject());
+            object.push(start());
         }
 
         protected T start() throws SAXException {
@@ -175,6 +169,9 @@
 
         public void endElement() throws SAXException {
             end(currentText.toString());
+            object.pop();
+            parentElement.pop();
+            parentObject.pop();
         }
 
         protected void text(char[] c, int start, int length) {
@@ -186,32 +183,37 @@
     private ParseMonitor monitor;
 
     public XMLParser(TopElementHandler rootHandler, ParseMonitor monitor) {
-        this.stack = new Stack<ElementHandler>();
+        this.stack = new Stack<>();
         this.monitor = monitor;
         this.stack.push(rootHandler);
     }
 
+    @Override
     public void setDocumentLocator(Locator locator) {
-        if (monitor != null) {
-            monitor.setState("Starting parsing");
-        }
+
     }
 
+    @Override
     public void startDocument() throws SAXException {
     }
 
+    @Override
     public void endDocument() throws SAXException {
     }
 
+    @Override
     public void startPrefixMapping(String prefix, String uri) throws SAXException {
     }
 
+    @Override
     public void endPrefixMapping(String prefix) throws SAXException {
     }
 
+    @SuppressWarnings("unchecked")
+    @Override
     public void startElement(String uri, String localName, String qName, Attributes atts) throws SAXException {
+        assert !stack.isEmpty();
 
-        assert !stack.isEmpty();
         ElementHandler parent = stack.peek();
         if (parent != null) {
             ElementHandler child = parent.getChild(qName);
@@ -225,6 +227,7 @@
         stack.push(null);
     }
 
+    @Override
     public void endElement(String uri, String localName, String qName) throws SAXException {
         ElementHandler handler = stack.pop();
         if (handler != null) {
@@ -232,6 +235,7 @@
         }
     }
 
+    @Override
     public void characters(char[] ch, int start, int length) throws SAXException {
 
         assert !stack.isEmpty();
@@ -243,12 +247,15 @@
         }
     }
 
+    @Override
     public void ignorableWhitespace(char[] ch, int start, int length) throws SAXException {
     }
 
+    @Override
     public void processingInstruction(String target, String data) throws SAXException {
     }
 
+    @Override
     public void skippedEntity(String name) throws SAXException {
     }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/serialization/XMLWriter.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/serialization/XMLWriter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2008, 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
@@ -41,7 +41,7 @@
 
     public XMLWriter(Writer inner) {
         this.inner = inner;
-        elementStack = new Stack<String>();
+        elementStack = new Stack<>();
     }
 
     @Override
@@ -49,6 +49,7 @@
         write(arr, 0, arr.length);
     }
 
+    @Override
     public void write(char[] cbuf, int off, int len) throws IOException {
         for (int i = off; i < off + len; i++) {
             char c = cbuf[i];
@@ -64,10 +65,12 @@
         }
     }
 
+    @Override
     public void flush() throws IOException {
         inner.flush();
     }
 
+    @Override
     public void close() throws IOException {
         inner.close();
     }
@@ -111,7 +114,7 @@
     }
 
     public void writeProperties(Properties props) throws IOException {
-        if (props.getProperties().hasNext() == false) {
+        if (props.iterator().hasNext() == false) {
             return;
         }
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/serialization/graphdocument.xsd	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,150 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema" elementFormDefault="qualified">
+    
+    <xsd:element name="graphDocument">
+        <xsd:complexType>
+            <xsd:sequence>
+                <xsd:element name="properties" type="propertiesType" minOccurs="0" maxOccurs="1" />
+                <xsd:element name="group" type="groupType" minOccurs="0" maxOccurs="unbounded" />
+            </xsd:sequence>
+        </xsd:complexType>
+    </xsd:element>
+
+    <xsd:complexType name="groupType">
+        <xsd:sequence>
+            <xsd:element name="properties" type="propertiesType" minOccurs="0" maxOccurs="1" />
+            <xsd:element name="assembly" type="assemblyType" minOccurs="0" maxOccurs="1" />
+            <xsd:element name="method" type="methodType" minOccurs="0" maxOccurs="1" />
+            <xsd:choice minOccurs="0" maxOccurs="unbounded" >
+                <xsd:element name="graph" type="graphType" />
+                <xsd:element name="group" type="groupType" />
+            </xsd:choice>
+        </xsd:sequence>
+        <xsd:attribute name="difference" use="optional" />
+    </xsd:complexType>
+    
+    <xsd:complexType name="propertiesType">
+        <xsd:sequence>
+            <xsd:element name="p" minOccurs="0" maxOccurs="unbounded">
+                <xsd:complexType>
+                    <xsd:simpleContent>
+                        <xsd:extension base="xsd:string">
+                            <xsd:attribute name="name" use="required" />
+                        </xsd:extension>
+                    </xsd:simpleContent>
+                </xsd:complexType>
+            </xsd:element>
+        </xsd:sequence>
+    </xsd:complexType>
+    
+    <xsd:simpleType name="assemblyType">
+        <xsd:restriction base="xsd:string" />
+    </xsd:simpleType>
+    
+    <xsd:complexType name="methodType">
+        <xsd:all>
+            <xsd:element name="properties" type="propertiesType" minOccurs="0" maxOccurs="1" />
+            <xsd:element name="bytecodes" minOccurs="0" maxOccurs="1">
+                <xsd:simpleType>
+                    <xsd:restriction base="xsd:string" />
+                </xsd:simpleType>
+            </xsd:element>
+            <xsd:element name="inlined" minOccurs="0" maxOccurs="1">
+                <xsd:complexType>
+                    <xsd:sequence>
+                        <xsd:element name="method" type="methodType" minOccurs="0" maxOccurs="unbounded" />
+                    </xsd:sequence>
+                </xsd:complexType>
+            </xsd:element>
+        </xsd:all>
+        <xsd:attribute name="bci" type="xsd:int" use="required" />
+        <xsd:attribute name="shortName" type="xsd:string" use="required" />
+        <xsd:attribute name="name" type="xsd:string" use="required" />
+    </xsd:complexType>
+    
+    <xsd:complexType name="graphType">
+        <xsd:sequence>
+            <xsd:element name="properties" type="propertiesType" minOccurs="0" maxOccurs="1" />
+            
+            <xsd:element name="nodes" minOccurs="0" maxOccurs="1">
+                <xsd:complexType>
+                    <xsd:sequence>
+                        <xsd:choice minOccurs="0" maxOccurs="unbounded">
+                            <xsd:element name="node" type="nodeType" />
+                            <xsd:element name="removeNode" type="nodeRefType" />
+                        </xsd:choice>
+                    </xsd:sequence>
+                </xsd:complexType>
+            </xsd:element>
+            
+            <xsd:element name="edges" minOccurs="0" maxOccurs="1">
+                <xsd:complexType>
+                    <xsd:sequence>
+                        <xsd:choice minOccurs="0" maxOccurs="unbounded">
+                            <xsd:element name="edge" type="edgeType" />
+                            <xsd:element name="removeEdge" type="edgeType" />
+                        </xsd:choice>
+                    </xsd:sequence>
+                </xsd:complexType>
+            </xsd:element>
+            
+            <xsd:element name="controlFlow" type="controlFlowType" minOccurs="0" maxOccurs="1" />
+        </xsd:sequence>
+        
+        <xsd:attribute name="name" use="optional" />
+    </xsd:complexType>
+    
+    <xsd:complexType name="nodeType">
+        <xsd:sequence>
+            <xsd:element name="properties" type="propertiesType" minOccurs="0" maxOccurs="1" />
+        </xsd:sequence>
+        <xsd:attribute name="id" type="xsd:int" use="required" />
+    </xsd:complexType>
+    
+    <xsd:complexType name="nodeRefType">
+        <xsd:attribute name="id" type="xsd:int" use="required" />
+    </xsd:complexType>
+    
+    <xsd:complexType name="edgeType">
+        <xsd:attribute name="from" type="xsd:int" use="required" />
+        <xsd:attribute name="to" type="xsd:int" use="required" />
+        <xsd:attribute name="label" type="xsd:string" use="optional" />
+        <xsd:attribute name="type" type="xsd:string" use="optional" />
+        <xsd:attribute name="fromIndex" type="xsd:int" use="optional" />
+        
+        <!-- These are aliases and should be mutually exclusive -->
+        <xsd:attribute name="toIndex" type="xsd:int" use="optional" />
+        <xsd:attribute name="index" type="xsd:int" use="optional" />
+    </xsd:complexType>
+    
+    <xsd:complexType name="controlFlowType">
+        <xsd:sequence>
+            <xsd:element name="block" type="blockType" minOccurs="0" maxOccurs="unbounded" />
+        </xsd:sequence>
+    </xsd:complexType>
+    
+    <xsd:complexType name="blockType">
+        <xsd:all>
+            <xsd:element name="successors" minOccurs="0" maxOccurs="1">
+                <xsd:complexType>
+                    <xsd:sequence>
+                        <xsd:element name="successor" minOccurs="0" maxOccurs="unbounded">
+                            <xsd:complexType>
+                                <xsd:attribute name="name" type="xsd:string" use="required" />
+                            </xsd:complexType>
+                        </xsd:element>
+                    </xsd:sequence>
+                </xsd:complexType>
+            </xsd:element>
+            <xsd:element name="nodes" minOccurs="0" maxOccurs="1">
+                <xsd:complexType>
+                    <xsd:sequence>
+                        <xsd:element name="node" type="nodeRefType" minOccurs="0" maxOccurs="unbounded" />
+                    </xsd:sequence>
+                </xsd:complexType>
+            </xsd:element>    
+        </xsd:all>
+        
+        <xsd:attribute name="name" type="xsd:string" use="required" />
+    </xsd:complexType>
+</xsd:schema>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/services/GraphViewer.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/services/GraphViewer.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -31,5 +31,5 @@
  */
 public interface GraphViewer {
 
-    public void view(InputGraph graph);
+    public void view(InputGraph graph, boolean clone);
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/services/GroupCallback.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/services/GroupCallback.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2007, 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
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/services/GroupOrganizer.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,39 +0,0 @@
-/*
- * Copyright (c) 2008, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- *
- */
-package com.sun.hotspot.igv.data.services;
-
-import com.sun.hotspot.igv.data.Group;
-import com.sun.hotspot.igv.data.Pair;
-import java.util.List;
-
-/**
- *
- * @author Thomas Wuerthinger
- */
-public interface GroupOrganizer {
-
-    public String getName();
-
-    public List<Pair<String, List<Group>>> organize(List<String> subFolders, List<Group> groups);
-}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/services/GroupReceiver.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,35 +0,0 @@
-/*
- * Copyright (c) 2008, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- *
- */
-package com.sun.hotspot.igv.data.services;
-
-import java.awt.Component;
-
-/**
- *
- * @author Thomas Wuerthinger
- */
-public interface GroupReceiver {
-
-    public Component init(GroupCallback callback);
-}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/services/InputGraphProvider.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/services/InputGraphProvider.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2007, 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
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/services/Scheduler.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/src/com/sun/hotspot/igv/data/services/Scheduler.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2007, 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
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/test/unit/src/com/sun/hotspot/igv/data/ChangedEventTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,95 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+
+package com.sun.hotspot.igv.data;
+
+import static org.junit.Assert.assertEquals;
+import org.junit.*;
+
+/**
+ *
+ * @author Thomas Wuerthinger
+ */
+public class ChangedEventTest {
+
+    public ChangedEventTest() {
+    }
+
+    @BeforeClass
+    public static void setUpClass() throws Exception {
+    }
+
+    @AfterClass
+    public static void tearDownClass() throws Exception {
+    }
+
+    @Before
+    public void setUp() {
+    }
+
+    @After
+    public void tearDown() {
+    }
+
+    /**
+     * Test of addListener method, of class Event.
+     */
+    @Test
+    public void testBase() {
+
+        ChangedEvent<Integer> e = new ChangedEvent<>(5);
+        final int[] fireCount = new int[1];
+
+        e.addListener(new ChangedListener<Integer>() {
+            @Override
+            public void changed(Integer s) {
+                assertEquals(s.intValue(), 5);
+                fireCount[0]++;
+            }
+        });
+
+        e.fire();
+        assertEquals(1, fireCount[0]);
+
+        e.fire();
+        assertEquals(2, fireCount[0]);
+
+        e.beginAtomic();
+
+        e.fire();
+        assertEquals(2, fireCount[0]);
+
+        e.fire();
+        assertEquals(2, fireCount[0]);
+
+        e.fire();
+        assertEquals(2, fireCount[0]);
+
+        e.endAtomic();
+        assertEquals(3, fireCount[0]);
+
+    }
+
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/test/unit/src/com/sun/hotspot/igv/data/ControllableChangedListenerTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,93 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+
+package com.sun.hotspot.igv.data;
+
+import static org.junit.Assert.*;
+import org.junit.*;
+
+/**
+ *
+ * @author Thomas Wuerthinger
+ */
+public class ControllableChangedListenerTest {
+
+    public ControllableChangedListenerTest() {
+    }
+
+    @BeforeClass
+    public static void setUpClass() throws Exception {
+    }
+
+    @AfterClass
+    public static void tearDownClass() throws Exception {
+    }
+
+    @Before
+    public void setUp() {
+    }
+
+    @After
+    public void tearDown() {
+    }
+
+    /**
+     * Test of isEnabled method, of class ControllableChangedListener.
+     */
+    @Test
+    public void testBase() {
+
+        final boolean[] hasFired = new boolean[1];
+        final boolean[] shouldFire = new boolean[1];
+        final Integer[] valueToFire = new Integer[1];
+        ControllableChangedListener<Integer> l = new ControllableChangedListener<Integer>() {
+
+            @Override
+            public void filteredChanged(Integer value) {
+                assertTrue(shouldFire[0]);
+                assertEquals(valueToFire[0], value);
+                hasFired[0] = true;
+            }
+        };
+
+        shouldFire[0] = true;
+        valueToFire[0] = 1;
+        hasFired[0] = false;
+        l.changed(1);
+        assertTrue(hasFired[0]);
+
+        shouldFire[0] = false;
+        hasFired[0] = false;
+        l.setEnabled(false);
+        l.changed(1);
+        assertFalse(hasFired[0]);
+
+        shouldFire[0] = true;
+        valueToFire[0] = 1;
+        hasFired[0] = false;
+        l.setEnabled(true);
+        l.changed(1);
+        assertTrue(hasFired[0]);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/test/unit/src/com/sun/hotspot/igv/data/GroupTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,74 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+
+package com.sun.hotspot.igv.data;
+
+import java.util.Arrays;
+import java.util.HashSet;
+import static org.junit.Assert.assertEquals;
+import org.junit.*;
+
+/**
+ *
+ * @author Thomas Wuerthinger
+ */
+public class GroupTest {
+
+    public GroupTest() {
+    }
+
+    @BeforeClass
+    public static void setUpClass() throws Exception {
+
+    }
+
+    @AfterClass
+    public static void tearDownClass() throws Exception {
+    }
+
+    @Before
+    public void setUp() {
+    }
+
+    @After
+    public void tearDown() {
+    }
+
+    /**
+     * Test of getAllNodes method, of class Group.
+     */
+    @Test
+    public void testGetAllNodes() {
+        final Group g = new Group(null);
+        final InputGraph graph1 = new InputGraph("1");
+        final InputGraph graph2 = new InputGraph("2");
+        g.addElement(graph1);
+        g.addElement(graph2);
+        graph1.addNode(new InputNode(1));
+        graph1.addNode(new InputNode(2));
+        graph2.addNode(new InputNode(2));
+        graph2.addNode(new InputNode(3));
+        assertEquals(g.getAllNodes(), new HashSet(Arrays.asList(1, 2, 3)));
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/test/unit/src/com/sun/hotspot/igv/data/InputGraphTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,211 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+
+package com.sun.hotspot.igv.data;
+
+import java.util.Arrays;
+import java.util.List;
+import java.util.Map;
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertTrue;
+import org.junit.*;
+
+/**
+ *
+ * @author Thomas Wuerthinger
+ */
+public class InputGraphTest {
+
+    /**
+     *    1
+     *   / \
+     *  2   3
+     *   \  |  5
+     *    \ | /
+     *      4
+     */
+    private static InputGraph referenceGraph;
+
+    private static InputGraph emptyGraph;
+
+    private static final InputNode N1 = new InputNode(1);
+    private static final InputNode N2 = new InputNode(2);
+    private static final InputNode N3 = new InputNode(3);
+    private static final InputNode N4 = new InputNode(4);
+    private static final InputNode N5 = new InputNode(5);
+    private static final InputEdge E12 = new InputEdge((char)0, 1, 2);
+    private static final InputEdge E13 = new InputEdge((char)0, 1, 3);
+    private static final InputEdge E24 = new InputEdge((char)0, 2, 4);
+    private static final InputEdge E34 = new InputEdge((char)0, 3, 4);
+    private static final InputEdge E54 = new InputEdge((char)0, 5, 4);
+
+    public InputGraphTest() {
+    }
+
+    @BeforeClass
+    public static void setUpClass() throws Exception {
+        Group group = new Group(null);
+
+        emptyGraph = new InputGraph("emptyGraph");
+        group.addElement(emptyGraph);
+
+        referenceGraph = new InputGraph("referenceGraph");
+        group.addElement(referenceGraph);
+        referenceGraph.addNode(N1);
+        referenceGraph.addNode(N2);
+        referenceGraph.addNode(N3);
+        referenceGraph.addNode(N4);
+        referenceGraph.addNode(N5);
+
+        referenceGraph.addEdge(E12);
+        referenceGraph.addEdge(E13);
+        referenceGraph.addEdge(E24);
+        referenceGraph.addEdge(E34);
+        referenceGraph.addEdge(E54);
+    }
+
+    @AfterClass
+    public static void tearDownClass() throws Exception {
+    }
+
+    @Before
+    public void setUp() {
+    }
+
+    @After
+    public void tearDown() {
+    }
+
+    /**
+     * Test of equals method, of class InputGraph.
+     */
+    @Test
+    public void testEquals() {
+
+        Group parentA = new Group(null);
+        InputGraph a = new InputGraph("graph");
+        parentA.addElement(a);
+
+        Group parentB = new Group(null);
+        InputGraph b = new InputGraph("graph");
+        parentB.addElement(b);
+
+        InputGraph c = new InputGraph("graph");
+        parentB.addElement(b);
+
+        Util.assertGraphEquals(a, b);
+        Util.assertGraphEquals(b, c);
+
+        a.addNode(new InputNode(1));
+        Util.assertGraphNotEquals(a, b);
+
+        b.addNode(new InputNode(1));
+        Util.assertGraphEquals(a, b);
+    }
+
+    /**
+     * Test of findRootNodes method, of class InputGraph.
+     */
+    @Test
+    public void testFindRootNodes() {
+        assertTrue(emptyGraph.findRootNodes().isEmpty());
+
+        List<InputNode> result = referenceGraph.findRootNodes();
+        assertTrue(result.size() == 2);
+        assertTrue(result.contains(N1));
+        assertTrue(result.contains(N5));
+    }
+
+    /**
+     * Test of findAllOutgoingEdges method, of class InputGraph.
+     */
+    @Test
+    public void testFindAllOutgoingEdges() {
+        assertTrue(emptyGraph.findAllOutgoingEdges().isEmpty());
+
+        Map<InputNode, List<InputEdge>> result = referenceGraph.findAllOutgoingEdges();
+        assertTrue(result.size() == 5);
+        assertEquals(result.get(N1), Arrays.asList(E12, E13));
+        assertEquals(result.get(N2), Arrays.asList(E24));
+        assertEquals(result.get(N3), Arrays.asList(E34));
+        assertEquals(result.get(N4), Arrays.asList());
+        assertEquals(result.get(N5), Arrays.asList(E54));
+    }
+
+    /**
+     * Test of findAllIngoingEdges method, of class InputGraph.
+     */
+    @Test
+    public void testFindAllIngoingEdges() {
+        assertTrue(emptyGraph.findAllIngoingEdges().isEmpty());
+
+        Map<InputNode, List<InputEdge>> result = referenceGraph.findAllIngoingEdges();
+        assertTrue(result.size() == 5);
+        assertEquals(result.get(N1), Arrays.asList());
+        assertEquals(result.get(N2), Arrays.asList(E12));
+        assertEquals(result.get(N3), Arrays.asList(E13));
+        assertEquals(result.get(N4), Arrays.asList(E24, E34, E54));
+        assertEquals(result.get(N5), Arrays.asList());
+    }
+
+    /**
+     * Test of findOutgoingEdges method, of class InputGraph.
+     */
+    @Test
+    public void testFindOutgoingEdges() {
+        assertTrue(emptyGraph.findOutgoingEdges(new InputNode(1)).isEmpty());
+
+        assertEquals(referenceGraph.findOutgoingEdges(N1), Arrays.asList(E12, E13));
+        assertEquals(referenceGraph.findOutgoingEdges(N2), Arrays.asList(E24));
+        assertEquals(referenceGraph.findOutgoingEdges(N3), Arrays.asList(E34));
+        assertEquals(referenceGraph.findOutgoingEdges(N4), Arrays.asList());
+        assertEquals(referenceGraph.findOutgoingEdges(N5), Arrays.asList(E54));
+    }
+
+    /**
+     * Test of getNext method, of class InputGraph.
+     */
+    @Test
+    public void testGetNextPrev() {
+        final Group group = new Group(null);
+
+        final InputGraph a = new InputGraph("a");
+
+        final InputGraph b = new InputGraph("b");
+
+        final InputGraph c = new InputGraph("c");
+        group.addElement(a);
+        group.addElement(b);
+        group.addElement(c);
+
+        assertEquals(null, a.getPrev());
+        assertEquals(b, a.getNext());
+
+        assertEquals(a, b.getPrev());
+        assertEquals(c, b.getNext());
+
+        assertEquals(b, c.getPrev());
+        assertEquals(null, c.getNext());
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/test/unit/src/com/sun/hotspot/igv/data/InputMethodTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,93 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+
+package com.sun.hotspot.igv.data;
+
+import static org.hamcrest.CoreMatchers.is;
+import static org.hamcrest.CoreMatchers.nullValue;
+import static org.junit.Assert.assertThat;
+import org.junit.*;
+
+/**
+ *
+ * @author Thomas
+ */
+public class InputMethodTest {
+
+    public InputMethodTest() {
+    }
+
+    @BeforeClass
+    public static void setUpClass() throws Exception {
+    }
+
+    @AfterClass
+    public static void tearDownClass() throws Exception {
+    }
+
+    @Before
+    public void setUp() {
+    }
+
+    @After
+    public void tearDown() {
+    }
+
+
+    /**
+     * Test of getBytecodes method, of class InputMethod.
+     */
+    @Test
+    public void testGetSetBytecodes() {
+
+        final String input = "0 iload_0\n" +
+                             "1 iconst_1\n" +
+                             "2 if_icmpne 7\n" +
+                             "5 iconst_1\n" +
+                             "6 ireturn\n" +
+                             "7 iconst_0\n" +
+                             "8 ireturn";
+
+        final Group g = new Group(null);
+        InputMethod m = new InputMethod(g, "name", "shortName", -1);
+        m.setBytecodes(input);
+
+        assertThat(m.getBytecodes().size(), is(7));
+
+        assertThat(m.getBytecodes().get(0).getBci(), is(0));
+        assertThat(m.getBytecodes().get(1).getBci(), is(1));
+        assertThat(m.getBytecodes().get(2).getBci(), is(2));
+        assertThat(m.getBytecodes().get(3).getBci(), is(5));
+
+        assertThat(m.getBytecodes().get(0).getName(), is("iload_0"));
+        assertThat(m.getBytecodes().get(1).getName(), is("iconst_1"));
+        assertThat(m.getBytecodes().get(2).getName(), is("if_icmpne 7"));
+        assertThat(m.getBytecodes().get(6).getName(), is("ireturn"));
+
+        assertThat(m.getBytecodes().get(2).getInlined(), nullValue());
+        assertThat(m.getBytecodes().get(6).getInlined(), nullValue());
+    }
+
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/test/unit/src/com/sun/hotspot/igv/data/PairTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,98 @@
+/*
+ * 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
+ * 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 com.sun.hotspot.igv.data;
+
+import static org.junit.Assert.*;
+import org.junit.*;
+
+/**
+ *
+ * @author Thomas Wuerthinger
+ */
+public class PairTest {
+
+    public PairTest() {
+    }
+
+    @BeforeClass
+    public static void setUpClass() throws Exception {
+    }
+
+    @AfterClass
+    public static void tearDownClass() throws Exception {
+    }
+
+    @Before
+    public void setUp() {
+    }
+
+    @After
+    public void tearDown() {
+    }
+
+    /**
+     * Test of getLeft method, of class Pair.
+     */
+    @Test
+    public void testBase() {
+        Pair p = new Pair();
+        assertTrue(p.getLeft() == null);
+        assertTrue(p.getRight() == null);
+        assertEquals("[null/null]", p.toString());
+        assertFalse(p.equals(null));
+
+        Pair<Integer, Integer> p2 = new Pair(1, 2);
+        assertTrue(p2.getLeft().intValue() == 1);
+        assertTrue(p2.getRight().intValue() == 2);
+        assertFalse(p.equals(p2));
+        assertFalse(p2.equals(p));
+        assertFalse(p.hashCode() == p2.hashCode());
+        assertEquals("[1/2]", p2.toString());
+
+        Pair p3 = new Pair(1, 2);
+        assertTrue(p2.equals(p3));
+        assertTrue(p2.hashCode() == p3.hashCode());
+
+        p2.setLeft(2);
+        assertFalse(p2.equals(p3));
+        assertTrue(p2.getLeft().intValue() == 2);
+        assertTrue(p2.getRight().intValue() == 2);
+        assertFalse(p2.hashCode() == p3.hashCode());
+        assertEquals("[2/2]", p2.toString());
+
+        p2.setRight(1);
+        assertFalse(p2.equals(p3));
+        assertTrue(p2.getLeft().intValue() == 2);
+        assertTrue(p2.getRight().intValue() == 1);
+        assertFalse(p2.hashCode() == p3.hashCode());
+        assertEquals("[2/1]", p2.toString());
+
+        p3.setLeft(2);
+        p3.setRight(1);
+        assertTrue(p2.hashCode() == p3.hashCode());
+        assertTrue(p2.equals(p3));
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/test/unit/src/com/sun/hotspot/igv/data/PropertiesTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,401 @@
+/*
+ * 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
+ * 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 com.sun.hotspot.igv.data;
+
+import com.sun.hotspot.igv.data.Properties.InvertPropertyMatcher;
+import com.sun.hotspot.igv.data.Properties.PropertyMatcher;
+import com.sun.hotspot.igv.data.Properties.PropertySelector;
+import com.sun.hotspot.igv.data.Properties.RegexpPropertyMatcher;
+import com.sun.hotspot.igv.data.Properties.StringPropertyMatcher;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Iterator;
+import junit.framework.TestCase;
+
+/**
+ *
+ * @author Thomas Wuerthinger
+ */
+public class PropertiesTest extends TestCase {
+
+
+
+    public PropertiesTest(String testName) {
+        super(testName);
+    }
+
+    @Override
+    protected void setUp() throws Exception {
+        super.setUp();
+    }
+
+    @Override
+    protected void tearDown() throws Exception {
+        super.tearDown();
+    }
+
+    /**
+     * Test of equals method, of class Properties.
+     */
+    public void testEquals() {
+        Properties a = new Properties();
+        assertFalse(a.equals(null));
+        assertTrue(a.equals(a));
+
+        Properties b = new Properties();
+        assertTrue(a.equals(b));
+        assertTrue(a.hashCode() == b.hashCode());
+
+        a.setProperty("p1", "1");
+        assertFalse(a.equals(b));
+        assertFalse(b.equals(a));
+        assertFalse(a.hashCode() == b.hashCode());
+
+        b.setProperty("p1", "1");
+        assertTrue(a.equals(b));
+        assertTrue(a.hashCode() == b.hashCode());
+
+        Properties c = new Properties(a);
+        assertTrue(c.equals(a));
+        assertTrue(c.equals(b));
+
+        c.setProperty("p1", "2");
+        assertFalse(c.equals(b));
+        assertFalse(c.hashCode() == b.hashCode());
+        assertFalse(c.equals(a));
+        assertFalse(c.hashCode() == a.hashCode());
+
+        a.setProperty("p2", "2");
+        Properties d = new Properties();
+        d.setProperty("p2", "2");
+        d.setProperty("p1", "1");
+        assertTrue(d.equals(a));
+    }
+
+    /**
+     * Test of selectSingle method, of class Properties.
+     */
+    public void testSelectSingle() {
+
+        final boolean[] called = new boolean[1];
+        final String v = "2";
+        final String n = "p2";
+
+        PropertyMatcher matcher = new PropertyMatcher() {
+
+            @Override
+            public String getName() {
+                assertFalse(called[0]);
+                called[0] = true;
+                return n;
+            }
+
+            @Override
+            public boolean match(String value) {
+                assertTrue(v.equals(value));
+                return true;
+            }
+        };
+
+        Properties instance = new Properties();
+        instance.setProperty("p1", "1");
+        instance.setProperty(n, v);
+        instance.setProperty("p3", "3");
+        Property result = instance.selectSingle(matcher);
+        assertEquals(result, new Property(n, v));
+
+
+        called[0] = false;
+        PropertyMatcher matcher2 = new PropertyMatcher() {
+
+            @Override
+            public String getName() {
+                assertFalse(called[0]);
+                called[0] = true;
+                return n;
+            }
+
+            @Override
+            public boolean match(String value) {
+                return false;
+            }
+        };
+
+
+        Property result2 = instance.selectSingle(matcher2);
+        assertTrue(result2 == null);
+    }
+
+    /**
+     * Test of get method, of class Properties.
+     */
+    public void testGet() {
+        Properties instance = new Properties();
+        instance.setProperty("p1", "1");
+        assertEquals("1", instance.get("p1"));
+        assertEquals(null, instance.get("p2"));
+    }
+
+    /**
+     * Test of getProperties method, of class Properties.
+     */
+    public void testIterator() {
+        Properties instance = new Properties();
+        instance.setProperty("p1", "1");
+        instance.setProperty("p2", "2");
+        Iterator<Property> result = instance.iterator();
+        assertTrue(result.hasNext());
+        assertEquals(new Property("p1", "1"), result.next());
+        assertTrue(result.hasNext());
+        assertEquals(new Property("p2", "2"), result.next());
+        assertFalse(result.hasNext());
+        assertTrue(result.next() == null);
+
+        try {
+            result.remove();
+            fail();
+        } catch(UnsupportedOperationException e) {}
+    }
+
+    /**
+     * Test of add method, of class Properties.
+     */
+    public void testAdd() {
+        Properties a = new Properties();
+        a.setProperty("p1", "1");
+        a.setProperty("p2", "2");
+
+        Properties b = new Properties();
+        b.setProperty("p1", "1");
+
+        Properties c = new Properties();
+        c.setProperty("p2", "2");
+
+        assertFalse(a.equals(b));
+        b.add(c);
+
+        assertTrue(a.equals(b));
+
+        b.setProperty("p3", null);
+        assertTrue(a.equals(b));
+
+        Properties empty = new Properties();
+        b.add(empty);
+        assertTrue(a.equals(b));
+
+        empty.add(b);
+        assertTrue(a.equals(empty));
+    }
+
+
+    /**
+     * Test the multiple argument constructors.
+     */
+    public void testConstructors() {
+        Properties a = new Properties("p1", "1", "p2", "2", "p3", "3");
+        Properties b = new Properties("p1", "1", "p2", "2");
+        Properties c = new Properties("p1", "1");
+
+        assertTrue(a.get("p3").equals("3"));
+        assertTrue(b.get("p2").equals("2"));
+        assertTrue(b.get("p1").equals("1"));
+
+        b.setProperty("p3", "3");
+        c.setProperty("p2", "2");
+        c.setProperty("p3", "3");
+
+        assertTrue(a.equals(b));
+        assertTrue(a.equals(c));
+    }
+
+    /**
+     * Test Entity class
+     */
+    public void testEntity() {
+
+        Properties p = new Properties();
+
+        Properties.Entity entity = new Properties.Entity();
+        assertEquals(entity.getProperties(), p);
+
+        entity.getProperties().setProperty("p1", "1");
+        Properties.Entity entity2 = new Properties.Entity(entity);
+        assertEquals(entity.getProperties(), entity2.getProperties());
+    }
+
+    /**
+     * Test property selector
+     */
+    public void testPropertySelector() {
+        final Collection<Properties.Entity> c = new ArrayList<>();
+
+        final Properties.Entity e1 = new Properties.Entity();
+        e1.getProperties().setProperty("p1", "1");
+        e1.getProperties().setProperty("p2", "2");
+        c.add(e1);
+
+        final Properties.Entity e2 = new Properties.Entity();
+        e2.getProperties().setProperty("p2", "2");
+        e2.getProperties().setProperty("p1", "1");
+        e2.getProperties().setProperty("p3", "3");
+        c.add(e2);
+
+        final Properties.Entity e3 = new Properties.Entity();
+        e3.getProperties().setProperty("p3", "3");
+        e3.getProperties().setProperty("p4", "4");
+        c.add(e3);
+
+        final PropertySelector<Properties.Entity> sel = new PropertySelector<>(c);
+
+        final StringPropertyMatcher matcher1 = new StringPropertyMatcher("p2", "2");
+        assertTrue(sel.selectMultiple(matcher1).size() == 2);
+        assertTrue(sel.selectMultiple(matcher1).contains(e1));
+        assertTrue(sel.selectMultiple(matcher1).contains(e2));
+        assertTrue(sel.selectSingle(matcher1).equals(e1) || sel.selectSingle(matcher1).equals(e2));
+
+        final StringPropertyMatcher matcher2 = new StringPropertyMatcher("p3", "3");
+        assertTrue(sel.selectMultiple(matcher2).size() == 2);
+        assertTrue(sel.selectMultiple(matcher2).contains(e2));
+        assertTrue(sel.selectMultiple(matcher2).contains(e3));
+        assertTrue(sel.selectSingle(matcher2).equals(e2) || sel.selectSingle(matcher2).equals(e3));
+
+        final StringPropertyMatcher matcher3 = new StringPropertyMatcher("p4", "4");
+        assertTrue(sel.selectMultiple(matcher3).size() == 1);
+        assertTrue(sel.selectMultiple(matcher3).contains(e3));
+        assertTrue(sel.selectSingle(matcher3).equals(e3));
+
+        final StringPropertyMatcher matcher4 = new StringPropertyMatcher("p5", "5");
+        assertTrue(sel.selectMultiple(matcher4).size() == 0);
+        assertTrue(sel.selectSingle(matcher4) == null);
+    }
+
+    public void testRemoveProperty() {
+        final Properties p = new Properties();
+        p.setProperty("p1", "1");
+        p.setProperty("p2", "2");
+
+        assertTrue(p.get("p1").equals("1"));
+        assertTrue(p.get("p2").equals("2"));
+
+        p.setProperty("p1", null);
+        assertTrue(p.get("p1") == null);
+        assertTrue(p.get("p2").equals("2"));
+
+        p.setProperty("p2", null);
+        assertTrue(p.get("p1") == null);
+        assertTrue(p.get("p2") == null);
+
+        p.setProperty("p3", "3");
+        assertTrue(p.get("p1") == null);
+        assertTrue(p.get("p2") == null);
+        assertTrue(p.get("p3").equals("3"));
+    }
+
+    /**
+     * Test property matchers
+     */
+    public void testPropertyMatchers() {
+        final StringPropertyMatcher matcher = new StringPropertyMatcher("p1", "1");
+        assertTrue(matcher.getName().equals("p1"));
+        assertTrue(matcher.match("1"));
+        assertFalse(matcher.match("2"));
+        try {
+            matcher.match(null);
+            fail();
+        } catch(IllegalArgumentException e) {}
+
+        try {
+            new StringPropertyMatcher(null, "**");
+            fail();
+        } catch(IllegalArgumentException e) {}
+
+        try {
+            new StringPropertyMatcher("p1", null);
+            fail();
+        } catch(IllegalArgumentException e) {}
+
+        final RegexpPropertyMatcher matcher2 = new RegexpPropertyMatcher("p1", "C.*");
+        assertTrue(matcher2.getName().equals("p1"));
+        assertTrue(matcher2.match("C"));
+        assertTrue(matcher2.match("Casdf"));
+        assertFalse(matcher2.match(" C"));
+        assertFalse(matcher2.match("c"));
+        assertFalse(matcher2.match("asdfC"));
+
+        try {
+            matcher2.match(null);
+            fail();
+        } catch(IllegalArgumentException e) {}
+
+        try {
+            new RegexpPropertyMatcher("p1", "**");
+            fail();
+        } catch(IllegalArgumentException e) {}
+
+        try {
+            new RegexpPropertyMatcher(null, "1");
+            fail();
+        } catch(IllegalArgumentException e) {}
+
+        try {
+            new RegexpPropertyMatcher("p1", null);
+            fail();
+        } catch(IllegalArgumentException e) {}
+
+        final InvertPropertyMatcher matcher3 = new InvertPropertyMatcher(matcher);
+        assertTrue(matcher3.getName().equals("p1"));
+        assertFalse(matcher3.match("1"));
+        assertTrue(matcher3.match("2"));
+        assertFalse(matcher3.match(null));
+    }
+
+    public void testToString() {
+        Properties p = new Properties();
+        assertEquals(p.toString(), "[]");
+
+        p.setProperty("p1", "1");
+        assertEquals(p.toString(), "[p1=1]");
+
+        Properties p2 = new Properties();
+        p2.setProperty("p1", "1");
+        p2.setProperty("p2", "2");
+        assertEquals(p2.toString(), "[p1=1, p2=2]");
+
+        Properties p3 = new Properties();
+        p3.setProperty("p2", "2");
+        p3.setProperty("p1", "1");
+        assertEquals(p3.toString(), "[p1=1, p2=2]");
+
+        p3.setProperty("p0", "0");
+        assertEquals(p3.toString(), "[p0=0, p1=1, p2=2]");
+
+        p2.setProperty("p1", null);
+        assertEquals(p2.toString(), "[p2=2]");
+
+        p2.setProperty("p2", null);
+        assertEquals(p2.toString(), "[]");
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/test/unit/src/com/sun/hotspot/igv/data/PropertyTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,116 @@
+/*
+ * 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
+ * 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 com.sun.hotspot.igv.data;
+
+import static org.junit.Assert.*;
+import org.junit.*;
+
+/**
+ *
+ * @author Thomas Wuerthinger
+ */
+public class PropertyTest {
+
+    public PropertyTest() {
+    }
+
+    @BeforeClass
+    public static void setUpClass() throws Exception {
+    }
+
+    @AfterClass
+    public static void tearDownClass() throws Exception {
+    }
+
+    @Before
+    public void setUp() {
+    }
+
+    @After
+    public void tearDown() {
+    }
+
+    /**
+     * Test of getName method, of class Property.
+     */
+    @Test
+    public void testGetNameAndValue() {
+        final Property p = new Property("name", "value");
+        assertEquals(p.getName(), "name");
+        assertEquals(p.getValue(), "value");
+
+        try {
+            new Property(null, "value");
+            fail();
+        } catch(IllegalArgumentException e) {
+        }
+
+
+        try {
+            new Property("name", null);
+            fail();
+        } catch(IllegalArgumentException e) {
+        }
+    }
+
+    /**
+     * Test of toString method, of class Property.
+     */
+    @Test
+    public void testToString() {
+        final Property p = new Property("name", "value");
+        assertEquals(p.toString(), "name=value");
+    }
+
+    /**
+     * Test of equals method, of class Property.
+     */
+    @Test
+    public void testEquals() {
+        final Property p = new Property("name", "value");
+        final Object o = new Object();
+        assertFalse(p.equals(o));
+        assertFalse(p.equals(null));
+        assertTrue(p.equals(p));
+
+        final Property p2 = new Property("name", "value1");
+        assertFalse(p.equals(p2));
+        assertTrue(p.hashCode() != p2.hashCode());
+
+        final Property p3 = new Property("name2", "value");
+        assertFalse(p.equals(p3));
+        assertTrue(p.hashCode() != p3.hashCode());
+        assertTrue(p2.hashCode() != p3.hashCode());
+
+        final Property p4 = new Property("name", "value");
+        assertEquals(p, p4);
+        assertEquals(p.hashCode(), p4.hashCode());
+
+        final Property p5 = new Property("value", "name");
+        assertFalse(p.equals(p5));
+        assertTrue(p.hashCode() != p5.hashCode());
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/test/unit/src/com/sun/hotspot/igv/data/SourceTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,79 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+
+package com.sun.hotspot.igv.data;
+
+import java.util.Arrays;
+import java.util.LinkedHashSet;
+import static org.junit.Assert.assertEquals;
+import org.junit.*;
+
+/**
+ *
+ * @author Thomas
+ */
+public class SourceTest {
+
+    public SourceTest() {
+    }
+
+    @BeforeClass
+    public static void setUpClass() throws Exception {
+    }
+
+    @AfterClass
+    public static void tearDownClass() throws Exception {
+    }
+
+    @Before
+    public void setUp() {
+    }
+
+    @After
+    public void tearDown() {
+    }
+
+    /**
+     * Test of getSourceNodes method, of class Source.
+     */
+    @Test
+    public void testBase() {
+        final Source s = new Source();
+
+        final InputNode N1 = new InputNode(1);
+        final InputNode N2 = new InputNode(2);
+
+        s.addSourceNode(N1);
+        assertEquals(s.getSourceNodes(), Arrays.asList(N1));
+        assertEquals(s.getSourceNodesAsSet(), new LinkedHashSet<>(Arrays.asList(1)));
+
+        s.addSourceNode(N2);
+        assertEquals(s.getSourceNodes(), Arrays.asList(N1, N2));
+        assertEquals(s.getSourceNodesAsSet(), new LinkedHashSet<>(Arrays.asList(1, 2)));
+
+        s.addSourceNode(N1);
+        assertEquals(s.getSourceNodes(), Arrays.asList(N1, N2));
+        assertEquals(s.getSourceNodesAsSet(), new LinkedHashSet<>(Arrays.asList(1, 2)));
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/test/unit/src/com/sun/hotspot/igv/data/Util.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,126 @@
+/*
+ * 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
+ * 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 com.sun.hotspot.igv.data;
+
+import static org.junit.Assert.*;
+
+/**
+ *
+ * @author Thomas Wuerthinger
+ */
+public class Util {
+
+    public static void assertGraphDocumentNotEquals(GraphDocument a, GraphDocument b) {
+        try {
+            assertGraphDocumentEquals(a, b);
+        } catch(AssertionError e) {
+            return;
+        }
+
+        fail("Graphs documents are equal!");
+    }
+
+    public static void assertGraphDocumentEquals(GraphDocument a, GraphDocument b) {
+
+        if (a.getElements().size() != b.getElements().size()) {
+            fail();
+        }
+
+        int z = 0;
+        for (FolderElement e : b.getElements()) {
+
+            if (e instanceof Group) {
+                Group g = (Group) e;
+                Group thisG = (Group) a.getElements().get(z);
+                assertGroupEquals(thisG, g);
+            z++;
+            }
+        }
+    }
+
+    public static void assertGroupNotEquals(Group a, Group b) {
+        try {
+            assertGroupEquals(a, b);
+        } catch(AssertionError e) {
+            return;
+        }
+
+        fail("Groups are equal!");
+    }
+
+    public static void assertGroupEquals(Group a, Group b) {
+
+        if (a.getGraphsCount() != b.getGraphsCount()) {
+            fail();
+        }
+
+        int z = 0;
+        for (InputGraph graph : a.getGraphs()) {
+            InputGraph otherGraph = b.getGraphs().get(z);
+            assertGraphEquals(graph, otherGraph);
+            z++;
+        }
+
+        if (a.getMethod() == null || b.getMethod() == null) {
+            if (a.getMethod() != b.getMethod()) {
+                fail();
+            }
+        } else {
+            if (!a.getMethod().equals(b.getMethod())) {
+                fail();
+            }
+        }
+    }
+
+    public static void assertGraphNotEquals(InputGraph a, InputGraph b) {
+        try {
+            assertGraphEquals(a, b);
+        } catch(AssertionError e) {
+            return;
+        }
+
+        fail("Graphs are equal!");
+    }
+
+    public static void assertGraphEquals(InputGraph a, InputGraph b) {
+
+        if(!a.getNodesAsSet().equals(b.getNodesAsSet())) {
+            fail();
+        }
+
+        if (!a.getEdges().equals(b.getEdges())) {
+            fail();
+        }
+
+        if (a.getBlocks().equals(b.getBlocks())) {
+            fail();
+        }
+
+        for (InputNode n : a.getNodes()) {
+            assertEquals(a.getBlock(n), b.getBlock(n));
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Data/test/unit/src/com/sun/hotspot/igv/data/serialization/ParserTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,225 @@
+/*
+ * 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
+ * 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 com.sun.hotspot.igv.data.serialization;
+
+import com.sun.hotspot.igv.data.*;
+import java.io.*;
+import java.nio.channels.Channels;
+import static org.junit.Assert.assertTrue;
+import static org.junit.Assert.fail;
+import org.junit.*;
+import org.openide.util.Exceptions;
+import org.xml.sax.InputSource;
+import org.xml.sax.SAXException;
+
+/**
+ *
+ * @author Thomas Wuerthinger
+ */
+public class ParserTest {
+
+    public ParserTest() {
+    }
+
+    @BeforeClass
+    public static void setUpClass() throws Exception {
+    }
+
+    @AfterClass
+    public static void tearDownClass() throws Exception {
+    }
+
+    @Before
+    public void setUp() {
+    }
+
+    @After
+    public void tearDown() {
+    }
+
+    private void test(GraphDocument document) {
+        final Printer printer = new Printer();
+        final CharArrayWriter writer = new CharArrayWriter();
+        printer.export(writer, document);
+        test(document, writer.toString());
+    }
+
+    private void test(GraphDocument document, String xmlString) {
+        try {
+            InputStream in = new ByteArrayInputStream(xmlString.getBytes("UTF-8"));
+            try {
+                Parser parser = new Parser(Channels.newChannel(in));
+                final GraphDocument parsedDocument = parser.parse();
+                Util.assertGraphDocumentEquals(document, parsedDocument);
+            } catch (SAXException ex) {
+                fail(ex.toString());
+            }
+        } catch (UnsupportedEncodingException ex) {
+            Exceptions.printStackTrace(ex);
+        }
+    }
+
+    private void testBoth(GraphDocument document, String xmlString) {
+        test(document);
+        test(document, xmlString);
+    }
+
+    /**
+     * Test of graph document serialization
+     */
+    @Test
+    public void testSerialization() {
+        final GraphDocument doc = new GraphDocument();
+
+        test(doc);
+
+        final Group group1 = new Group(doc);
+        doc.addElement(group1);
+        test(doc);
+
+        final Group group2 = new Group(doc);
+        doc.addElement(group2);
+        test(doc);
+
+        final InputGraph graph = new InputGraph("");
+        group1.addElement(graph);
+        test(doc);
+
+        graph.addNode(new InputNode(0));
+        test(doc);
+
+        graph.addNode(new InputNode(1));
+        test(doc);
+
+        graph.addNode(new InputNode(2));
+        test(doc);
+
+        graph.addNode(new InputNode(3));
+        test(doc);
+
+        graph.addEdge(new InputEdge((char)0, (char)0, 0, 1));
+        test(doc);
+
+        graph.addEdge(new InputEdge((char)1, (char)1, 0, 1));
+        test(doc);
+
+        graph.addEdge(new InputEdge((char)0, (char)0, 1, 2));
+        test(doc);
+
+        graph.addEdge(new InputEdge((char)0, (char)0, 2, 3));
+        test(doc);
+
+        group1.setMethod(new InputMethod(group1, "testMethod", "tM", 1));
+        test(doc);
+
+        final InputBlock b1 = graph.addBlock("1");
+        b1.addNode(0);
+        b1.addNode(1);
+
+        final InputBlock b2 = graph.addBlock("2");
+        b2.addNode(2);
+        b2.addNode(3);
+        test(doc);
+
+        final GraphDocument document2 = new GraphDocument();
+        doc.addGraphDocument(document2);
+        test(doc);
+        assertTrue(doc.getElements().size() == 2);
+
+        final Group group3 = new Group(document2);
+        document2.addElement(group3);
+        doc.addGraphDocument(document2);
+        assertTrue(doc.getElements().size() == 3);
+        assertTrue(document2.getElements().size() == 0);
+
+        doc.clear();
+        test(doc);
+        Util.assertGraphDocumentEquals(doc, new GraphDocument());
+    }
+
+    @Test
+    public void testSimpleExport() {
+        GraphDocument document = new GraphDocument();
+        Group g = new Group(document);
+        document.addElement(g);
+
+        InputGraph graph = new InputGraph("TestGraph");
+                g.addElement(graph);
+        graph.getProperties().setProperty("testName", "testValue");
+
+        InputNode n1 = new InputNode(0);
+        InputNode n2 = new InputNode(1);
+        InputEdge e1 = new InputEdge((char)0, 0, 1);
+        InputEdge e2 = new InputEdge((char)1, 0, 1);
+        graph.addNode(n1);
+        graph.addNode(n2);
+        graph.addEdge(e1);
+        graph.addEdge(e2);
+
+        test(document);
+    }
+
+    @Test
+    public void testComplexExport() {
+
+        GraphDocument document = new GraphDocument();
+        Group g = new Group(document);
+        document.addElement(g);
+
+        InputGraph graph = new InputGraph("TestGraph");
+                g.addElement(graph);
+        graph.getProperties().setProperty("testName", "testValue");
+
+        InputNode n1 = new InputNode(0);
+        InputNode n2 = new InputNode(1);
+        InputEdge e1 = new InputEdge((char)0, 0, 0);
+        InputEdge e2 = new InputEdge((char)1, 1, 1);
+        graph.addNode(n1);
+        graph.addNode(n2);
+        graph.addEdge(e1);
+        graph.addEdge(e2);
+
+        InputGraph graph2 = new InputGraph("TestGraph2");
+                g.addElement(graph2);
+        graph2.addNode(n1);
+        InputNode n3 = new InputNode(2);
+        graph2.addNode(n3);
+        InputEdge e3 = new InputEdge((char)0, 0, 2);
+        graph2.addEdge(e3);
+
+        test(document);
+    }
+
+
+    /**
+     * Test of parse method, of class Parser.
+     */
+    @Test
+    public void testParse() {
+        testBoth(new GraphDocument(), "<graphDocument></graphDocument>");
+    }
+
+}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Difference/nbproject/project.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Difference/nbproject/project.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,2 +1,2 @@
-javac.source=1.5
-javac.compilerargs=-Xlint -Xlint:-serial
+javac.source=1.7
+javac.compilerargs=-Xlint -Xlint:-serial
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Difference/nbproject/project.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Difference/nbproject/project.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -14,6 +14,14 @@
                         <specification-version>1.0</specification-version>
                     </run-dependency>
                 </dependency>
+                <dependency>
+                    <code-name-base>org.openide.util.lookup</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>8.6.1</specification-version>
+                    </run-dependency>
+                </dependency>
             </module-dependencies>
             <public-packages>
                 <package>com.sun.hotspot.igv.difference</package>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Difference/src/com/sun/hotspot/igv/difference/Difference.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Difference/src/com/sun/hotspot/igv/difference/Difference.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2008, 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
@@ -24,16 +24,11 @@
  */
 package com.sun.hotspot.igv.difference;
 
-import com.sun.hotspot.igv.data.Group;
-import com.sun.hotspot.igv.data.InputEdge;
-import com.sun.hotspot.igv.data.InputGraph;
-import com.sun.hotspot.igv.data.InputNode;
-import com.sun.hotspot.igv.data.Property;
-import java.util.Collection;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.Map;
-import java.util.Set;
+import com.sun.hotspot.igv.data.Properties;
+import com.sun.hotspot.igv.data.*;
+import com.sun.hotspot.igv.data.services.Scheduler;
+import java.util.*;
+import org.openide.util.Lookup;
 
 /**
  *
@@ -46,7 +41,7 @@
     public static final String VALUE_CHANGED = "changed";
     public static final String VALUE_SAME = "same";
     public static final String VALUE_DELETED = "deleted";
-    public static final String OLD_PREFIX = "OLD_";
+    public static final String NEW_PREFIX = "NEW_";
     public static final String MAIN_PROPERTY = "name";
     public static final double LIMIT = 100.0;
     public static final String[] IGNORE_PROPERTIES = new String[]{"idx", "debug_idx"};
@@ -60,14 +55,14 @@
     }
 
     private static InputGraph createDiffSameGroup(InputGraph a, InputGraph b) {
-        Map<Integer, InputNode> keyMapB = new HashMap<Integer, InputNode>();
+        Map<Integer, InputNode> keyMapB = new HashMap<>(b.getNodes().size());
         for (InputNode n : b.getNodes()) {
             Integer key = n.getId();
             assert !keyMapB.containsKey(key);
             keyMapB.put(key, n);
         }
 
-        Set<Pair> pairs = new HashSet<Pair>();
+        Set<NodePair> pairs = new HashSet<>();
 
         for (InputNode n : a.getNodes()) {
             Integer key = n.getId();
@@ -75,30 +70,92 @@
 
             if (keyMapB.containsKey(key)) {
                 InputNode nB = keyMapB.get(key);
-                pairs.add(new Pair(n, nB));
+                pairs.add(new NodePair(n, nB));
             }
         }
 
         return createDiff(a, b, pairs);
     }
 
-    private static InputGraph createDiff(InputGraph a, InputGraph b, Set<Pair> pairs) {
-        Group g = new Group();
+    private static void ensureScheduled(InputGraph a) {
+        if (a.getBlocks().isEmpty()) {
+            Scheduler s = Lookup.getDefault().lookup(Scheduler.class);
+            a.clearBlocks();
+            s.schedule(a);
+            a.ensureNodesInBlocks();
+        }
+    }
+
+    private static InputGraph createDiff(InputGraph a, InputGraph b, Set<NodePair> pairs) {
+        ensureScheduled(a);
+        ensureScheduled(b);
+
+        Group g = new Group(null);
         g.setMethod(a.getGroup().getMethod());
-        g.setAssembly(a.getGroup().getAssembly());
+        if (a.getGroup() == b.getGroup()) {
+            g.getProperties().add(a.getGroup().getProperties());
+        } else {
+            // copy properties that have the same value in both groups
+            Properties bps = b.getGroup().getProperties();
+            for (Property p : a.getGroup().getProperties()) {
+                String value = p.getValue();
+                if (value != null && value.equals(bps.get(p.getName()))) {
+                    g.getProperties().setProperty(p.getName(), value);
+                }
+            }
+        }
         g.getProperties().setProperty("name", "Difference");
-        InputGraph graph = new InputGraph(g, null);
-        graph.setName(a.getName() + ", " + b.getName());
-        graph.setIsDifferenceGraph(true);
+        InputGraph graph = new InputGraph(a.getName() + ", " + b.getName());
+        g.addElement(graph);
 
-        Set<InputNode> nodesA = new HashSet<InputNode>(a.getNodes());
-        Set<InputNode> nodesB = new HashSet<InputNode>(b.getNodes());
+        Map<InputBlock, InputBlock> blocksMap = new HashMap<>();
+        for (InputBlock blk : a.getBlocks()) {
+            InputBlock diffblk = graph.addBlock(blk.getName());
+            blocksMap.put(blk, diffblk);
+        }
+        for (InputBlock blk : b.getBlocks()) {
+            InputBlock diffblk = graph.getBlock(blk.getName());
+            if (diffblk == null) {
+                diffblk = graph.addBlock(blk.getName());
+            }
+            blocksMap.put(blk, diffblk);
+        }
 
-        Map<InputNode, InputNode> inputNodeMap = new HashMap<InputNode, InputNode>();
-        for (Pair p : pairs) {
-            InputNode n = p.getN1();
+        // Difference between block edges
+        Set<Pair<String, String>> aEdges = new HashSet<>();
+        for (InputBlockEdge edge : a.getBlockEdges()) {
+            aEdges.add(new Pair<>(edge.getFrom().getName(), edge.getTo().getName()));
+        }
+        for (InputBlockEdge bEdge : b.getBlockEdges()) {
+            InputBlock from = bEdge.getFrom();
+            InputBlock to = bEdge.getTo();
+            Pair<String, String> pair = new Pair<>(from.getName(), to.getName());
+            if (aEdges.contains(pair)) {
+                // same
+                graph.addBlockEdge(blocksMap.get(from), blocksMap.get(to));
+                aEdges.remove(pair);
+            } else {
+                // added
+                InputBlockEdge edge = graph.addBlockEdge(blocksMap.get(from), blocksMap.get(to));
+                edge.setState(InputBlockEdge.State.NEW);
+            }
+        }
+        for (Pair<String, String> deleted : aEdges) {
+            // removed
+            InputBlock from = graph.getBlock(deleted.getLeft());
+            InputBlock to = graph.getBlock(deleted.getRight());
+            InputBlockEdge edge = graph.addBlockEdge(from, to);
+            edge.setState(InputBlockEdge.State.DELETED);
+        }
+
+        Set<InputNode> nodesA = new HashSet<>(a.getNodes());
+        Set<InputNode> nodesB = new HashSet<>(b.getNodes());
+
+        Map<InputNode, InputNode> inputNodeMap = new HashMap<>(pairs.size());
+        for (NodePair p : pairs) {
+            InputNode n = p.getLeft();
             assert nodesA.contains(n);
-            InputNode nB = p.getN2();
+            InputNode nB = p.getRight();
             assert nodesB.contains(nB);
 
             nodesA.remove(n);
@@ -107,41 +164,59 @@
             inputNodeMap.put(n, n2);
             inputNodeMap.put(nB, n2);
             graph.addNode(n2);
+            InputBlock block = blocksMap.get(a.getBlock(n));
+            block.addNode(n2.getId());
             markAsChanged(n2, n, nB);
         }
 
         for (InputNode n : nodesA) {
             InputNode n2 = new InputNode(n);
             graph.addNode(n2);
-            markAsNew(n2);
+            InputBlock block = blocksMap.get(a.getBlock(n));
+            block.addNode(n2.getId());
+            markAsDeleted(n2);
             inputNodeMap.put(n, n2);
         }
 
+        int curIndex = 0;
         for (InputNode n : nodesB) {
             InputNode n2 = new InputNode(n);
-            n2.setId(-n2.getId());
+
+            // Find new ID for node of b, does not change the id property
+            while (graph.getNode(curIndex) != null) {
+                curIndex++;
+            }
+
+            n2.setId(curIndex);
             graph.addNode(n2);
-            markAsDeleted(n2);
+            InputBlock block = blocksMap.get(b.getBlock(n));
+            block.addNode(n2.getId());
+            markAsNew(n2);
             inputNodeMap.put(n, n2);
         }
 
         Collection<InputEdge> edgesA = a.getEdges();
         Collection<InputEdge> edgesB = b.getEdges();
 
-        Set<InputEdge> newEdges = new HashSet<InputEdge>();
+        Set<InputEdge> newEdges = new HashSet<>();
 
         for (InputEdge e : edgesA) {
             int from = e.getFrom();
             int to = e.getTo();
             InputNode nodeFrom = inputNodeMap.get(a.getNode(from));
             InputNode nodeTo = inputNodeMap.get(a.getNode(to));
-            char index = e.getToIndex();
+            char fromIndex = e.getFromIndex();
+            char toIndex = e.getToIndex();
 
-            InputEdge newEdge = new InputEdge(index, nodeFrom.getId(), nodeTo.getId());
-            if (!newEdges.contains(newEdge)) {
-                markAsNew(newEdge);
-                newEdges.add(newEdge);
-                graph.addEdge(newEdge);
+            if (nodeFrom == null || nodeTo == null) {
+                System.out.println("Unexpected edge : " + from + " -> " + to);
+            } else {
+                InputEdge newEdge = new InputEdge(fromIndex, toIndex, nodeFrom.getId(), nodeTo.getId(), e.getLabel(), e.getType());
+                if (!newEdges.contains(newEdge)) {
+                    markAsDeleted(newEdge);
+                    newEdges.add(newEdge);
+                    graph.addEdge(newEdge);
+                }
             }
         }
 
@@ -150,40 +225,41 @@
             int to = e.getTo();
             InputNode nodeFrom = inputNodeMap.get(b.getNode(from));
             InputNode nodeTo = inputNodeMap.get(b.getNode(to));
-            char index = e.getToIndex();
+            char fromIndex = e.getFromIndex();
+            char toIndex = e.getToIndex();
 
-            InputEdge newEdge = new InputEdge(index, nodeFrom.getId(), nodeTo.getId());
-            if (!newEdges.contains(newEdge)) {
-                markAsDeleted(newEdge);
-                newEdges.add(newEdge);
-                graph.addEdge(newEdge);
+            if (nodeFrom == null || nodeTo == null) {
+                System.out.println("Unexpected edge : " + from + " -> " + to);
             } else {
-                newEdges.remove(newEdge);
-                graph.removeEdge(newEdge);
-                markAsSame(newEdge);
-                newEdges.add(newEdge);
-                graph.addEdge(newEdge);
+                InputEdge newEdge = new InputEdge(fromIndex, toIndex, nodeFrom.getId(), nodeTo.getId(), e.getLabel(), e.getType());
+                if (!newEdges.contains(newEdge)) {
+                    markAsNew(newEdge);
+                    newEdges.add(newEdge);
+                    graph.addEdge(newEdge);
+                } else {
+                    newEdges.remove(newEdge);
+                    graph.removeEdge(newEdge);
+                    markAsSame(newEdge);
+                    newEdges.add(newEdge);
+                    graph.addEdge(newEdge);
+                }
             }
         }
 
-        g.addGraph(graph);
         return graph;
     }
 
-    private static class Pair {
+    private static class NodePair extends Pair<InputNode, InputNode> {
+
 
-        private InputNode n1;
-        private InputNode n2;
-
-        public Pair(InputNode n1, InputNode n2) {
-            this.n1 = n1;
-            this.n2 = n2;
+        public NodePair(InputNode n1, InputNode n2) {
+            super(n1, n2);
         }
 
         public double getValue() {
 
             double result = 0.0;
-            for (Property p : n1.getProperties()) {
+            for (Property p : getLeft().getProperties()) {
                 double faktor = 1.0;
                 for (String forbidden : IGNORE_PROPERTIES) {
                     if (p.getName().equals(forbidden)) {
@@ -191,7 +267,7 @@
                         break;
                     }
                 }
-                String p2 = n2.getProperties().get(p.getName());
+                String p2 = getRight().getProperties().get(p.getName());
                 result += evaluate(p.getValue(), p2) * faktor;
             }
 
@@ -208,21 +284,13 @@
                 return (double) (Math.abs(p.length() - p2.length())) / p.length() + 0.5;
             }
         }
-
-        public InputNode getN1() {
-            return n1;
-        }
-
-        public InputNode getN2() {
-            return n2;
-        }
     }
 
     private static InputGraph createDiff(InputGraph a, InputGraph b) {
 
-        Set<InputNode> matched = new HashSet<InputNode>();
+        Set<InputNode> matched = new HashSet<>();
 
-        Set<Pair> pairs = new HashSet<Pair>();
+        Set<NodePair> pairs = new HashSet<>();
         for (InputNode n : a.getNodes()) {
             String s = n.getProperties().get(MAIN_PROPERTY);
             if (s == null) {
@@ -235,18 +303,18 @@
                 }
 
                 if (s.equals(s2)) {
-                    Pair p = new Pair(n, n2);
+                    NodePair p = new NodePair(n, n2);
                     pairs.add(p);
                 }
             }
         }
 
-        Set<Pair> selectedPairs = new HashSet<Pair>();
+        Set<NodePair> selectedPairs = new HashSet<>();
         while (pairs.size() > 0) {
 
             double min = Double.MAX_VALUE;
-            Pair minPair = null;
-            for (Pair p : pairs) {
+            NodePair minPair = null;
+            for (NodePair p : pairs) {
                 double cur = p.getValue();
                 if (cur < min) {
                     minPair = p;
@@ -259,9 +327,9 @@
             } else {
                 selectedPairs.add(minPair);
 
-                Set<Pair> toRemove = new HashSet<Pair>();
-                for (Pair p : pairs) {
-                    if (p.getN1() == minPair.getN1() || p.getN2() == minPair.getN2()) {
+                Set<NodePair> toRemove = new HashSet<>();
+                for (NodePair p : pairs) {
+                    if (p.getLeft() == minPair.getLeft() || p.getRight() == minPair.getRight()) {
                         toRemove.add(p);
                     }
                 }
@@ -292,7 +360,7 @@
             String s = firstNode.getProperties().get(p.getName());
             if (!p.getValue().equals(s)) {
                 difference = true;
-                n.getProperties().setProperty(OLD_PREFIX + p.getName(), p.getValue());
+                n.getProperties().setProperty(NEW_PREFIX + p.getName(), p.getValue());
             }
         }
 
@@ -300,7 +368,7 @@
             String s = otherNode.getProperties().get(p.getName());
             if (s == null && p.getValue().length() > 0) {
                 difference = true;
-                n.getProperties().setProperty(OLD_PREFIX + p.getName(), "");
+                n.getProperties().setProperty(NEW_PREFIX + p.getName(), "");
             }
         }
 
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/nbproject/project.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Filter/nbproject/project.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,2 +1,2 @@
-javac.source=1.5
-javac.compilerargs=-Xlint -Xlint:-serial
+javac.source=1.7
+javac.compilerargs=-Xlint -Xlint:-serial
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/nbproject/project.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Filter/nbproject/project.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -23,12 +23,28 @@
                     </run-dependency>
                 </dependency>
                 <dependency>
+                    <code-name-base>com.sun.hotspot.igv.layout</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>1.0</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
                     <code-name-base>org.jdesktop.layout</code-name-base>
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
                         <release-version>1</release-version>
-                        <specification-version>1.4.1</specification-version>
+                        <specification-version>1.16.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.awt</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>7.30.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -36,7 +52,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>7.5.1</specification-version>
+                        <specification-version>7.18.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -44,7 +60,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>7.3</specification-version>
+                        <specification-version>7.46.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -52,7 +68,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>7.2.0.1</specification-version>
+                        <specification-version>7.20.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -60,7 +76,15 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>7.9.0.1</specification-version>
+                        <specification-version>8.14.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.util.lookup</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>8.6.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -68,7 +92,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>6.16</specification-version>
+                        <specification-version>6.39.1</specification-version>
                     </run-dependency>
                 </dependency>
             </module-dependencies>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/META-INF/services/com.sun.hotspot.igv.filter.ScriptEngineAbstraction	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,1 +0,0 @@
-com.sun.hotspot.igv.filter.JavaSE6ScriptEngine
\ No newline at end of file
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/AbstractFilter.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/AbstractFilter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2007, 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
@@ -42,14 +42,17 @@
         properties = new Properties();
     }
 
+    @Override
     public Properties getProperties() {
         return properties;
     }
 
+    @Override
     public OpenCookie getEditor() {
         return null;
     }
 
+    @Override
     public ChangedEvent<Filter> getChangedEvent() {
         return changedEvent;
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/ColorFilter.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/ColorFilter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,13 +23,9 @@
  */
 package com.sun.hotspot.igv.filter;
 
-import com.sun.hotspot.igv.graph.Connection;
+import com.sun.hotspot.igv.data.Properties;
 import com.sun.hotspot.igv.graph.Connection.ConnectionStyle;
-import com.sun.hotspot.igv.graph.Diagram;
-import com.sun.hotspot.igv.graph.Figure;
-import com.sun.hotspot.igv.graph.OutputSlot;
-import com.sun.hotspot.igv.graph.Selector;
-import com.sun.hotspot.igv.data.Properties;
+import com.sun.hotspot.igv.graph.*;
 import java.awt.Color;
 import java.util.ArrayList;
 import java.util.List;
@@ -45,16 +41,18 @@
 
     public ColorFilter(String name) {
         this.name = name;
-        colorRules = new ArrayList<ColorRule>();
+        colorRules = new ArrayList<>();
     }
 
+    @Override
     public String getName() {
         return name;
     }
 
+    @Override
     public void apply(Diagram diagram) {
 
-        Properties.PropertySelector<Figure> selector = new Properties.PropertySelector<Figure>(diagram.getFigures());
+        Properties.PropertySelector<Figure> selector = new Properties.PropertySelector<>(diagram.getFigures());
         for (ColorRule rule : colorRules) {
             if (rule.getSelector() != null) {
                 List<Figure> figures = rule.getSelector().selected(diagram);
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/CombineFilter.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/CombineFilter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,13 +23,9 @@
  */
 package com.sun.hotspot.igv.filter;
 
-import com.sun.hotspot.igv.graph.Connection;
-import com.sun.hotspot.igv.graph.Diagram;
-import com.sun.hotspot.igv.graph.Figure;
-import com.sun.hotspot.igv.graph.InputSlot;
-import com.sun.hotspot.igv.graph.OutputSlot;
 import com.sun.hotspot.igv.data.Properties;
 import com.sun.hotspot.igv.data.Properties.PropertyMatcher;
+import com.sun.hotspot.igv.graph.*;
 import java.util.ArrayList;
 import java.util.HashSet;
 import java.util.List;
@@ -46,23 +42,25 @@
 
     public CombineFilter(String name) {
         this.name = name;
-        rules = new ArrayList<CombineRule>();
+        rules = new ArrayList<>();
     }
 
+    @Override
     public String getName() {
         return name;
     }
 
+    @Override
     public void apply(Diagram diagram) {
 
-        Properties.PropertySelector<Figure> selector = new Properties.PropertySelector<Figure>(diagram.getFigures());
+        Properties.PropertySelector<Figure> selector = new Properties.PropertySelector<>(diagram.getFigures());
         for (CombineRule r : rules) {
 
             List<Figure> list = selector.selectMultiple(r.getFirstMatcher());
-            Set<Figure> figuresToRemove = new HashSet<Figure>();
+            Set<Figure> figuresToRemove = new HashSet<>();
             for (Figure f : list) {
 
-                List<Figure> successors = new ArrayList<Figure>(f.getSuccessors());
+                List<Figure> successors = new ArrayList<>(f.getSuccessors());
                 if (r.isReversed()) {
                     if (successors.size() == 1) {
                         Figure succ = successors.get(0);
@@ -76,21 +74,30 @@
                             }
                         }
 
-                        assert slot != null;
-                        slot.setName(f.getProperties().get("dump_spec"));
-                        if (f.getProperties().get("short_name") != null) {
-                            slot.setShortName(f.getProperties().get("short_name"));
+                        slot.getSource().addSourceNodes(f.getSource());
+                        if (r.getShortProperty() != null) {
+                            String s = f.getProperties().get(r.getShortProperty());
+                            if (s != null && s.length() > 0) {
+                                slot.setShortName(s);
+                                slot.setText(s);
+                                slot.setColor(f.getColor());
+                            }
                         } else {
-                            String s = f.getProperties().get("dump_spec");
-                            if (s != null && s.length() <= 5) {
-                                slot.setShortName(s);
+                            assert slot != null;
+                            slot.setText(f.getProperties().get("dump_spec"));
+                            if (f.getProperties().get("short_name") != null) {
+                                slot.setShortName(f.getProperties().get("short_name"));
+                            } else {
+                                String s = f.getProperties().get("dump_spec");
+                                if (s != null && s.length() <= 5) {
+                                    slot.setShortName(s);
+                                }
                             }
-
                         }
 
                         for (InputSlot s : f.getInputSlots()) {
                             for (Connection c : s.getConnections()) {
-                                Connection newConn = diagram.createConnection(slot, c.getOutputSlot());
+                                Connection newConn = diagram.createConnection(slot, c.getOutputSlot(), c.getLabel(), c.getType());
                                 newConn.setColor(c.getColor());
                                 newConn.setStyle(c.getStyle());
                             }
@@ -101,7 +108,7 @@
                 } else {
 
                     for (Figure succ : successors) {
-                        if (succ.getPredecessors().size() == 1) {
+                        if (succ.getPredecessors().size() == 1 && succ.getInputSlots().size() == 1) {
                             if (succ.getProperties().selectSingle(r.getSecondMatcher()) != null && succ.getOutputSlots().size() == 1) {
 
 
@@ -122,22 +129,32 @@
                                     pos = Integer.parseInt(succ.getProperties().get("con"));
                                 }
                                 OutputSlot slot = f.createOutputSlot(pos);
-                                slot.setName(succ.getProperties().get("dump_spec"));
-                                if (succ.getProperties().get("short_name") != null) {
-                                    slot.setShortName(succ.getProperties().get("short_name"));
+                                slot.getSource().addSourceNodes(succ.getSource());
+                                if (r.getShortProperty() != null) {
+                                    String s = succ.getProperties().get(r.getShortProperty());
+                                    if (s != null && s.length() > 0) {
+                                        slot.setShortName(s);
+                                        slot.setText(s);
+                                        slot.setColor(succ.getColor());
+                                    }
                                 } else {
-                                    String s = succ.getProperties().get("dump_spec");
-                                    if (s != null && s.length() <= 2) {
-                                        slot.setShortName(s);
+                                    slot.setText(succ.getProperties().get("dump_spec"));
+                                    if (succ.getProperties().get("short_name") != null) {
+                                        slot.setShortName(succ.getProperties().get("short_name"));
                                     } else {
-                                        String tmpName = succ.getProperties().get("name");
-                                        if (tmpName != null && tmpName.length() > 0) {
-                                            slot.setShortName(tmpName.substring(0, 1));
+                                        String s = succ.getProperties().get("dump_spec");
+                                        if (s != null && s.length() <= 2) {
+                                            slot.setShortName(s);
+                                        } else {
+                                            String tmpName = succ.getProperties().get("name");
+                                            if (tmpName != null && tmpName.length() > 0) {
+                                                slot.setShortName(tmpName.substring(0, 1));
+                                            }
                                         }
                                     }
                                 }
                                 for (Connection c : nextSlot.getConnections()) {
-                                    Connection newConn = diagram.createConnection(c.getInputSlot(), slot);
+                                    Connection newConn = diagram.createConnection(c.getInputSlot(), slot, c.getLabel(), c.getType());
                                     newConn.setColor(c.getColor());
                                     newConn.setStyle(c.getStyle());
                                 }
@@ -167,6 +184,7 @@
         private PropertyMatcher first;
         private PropertyMatcher second;
         private boolean reversed;
+        private String shortProperty;
 
         public CombineRule(PropertyMatcher first, PropertyMatcher second) {
             this(first, second, false);
@@ -174,9 +192,14 @@
         }
 
         public CombineRule(PropertyMatcher first, PropertyMatcher second, boolean reversed) {
+            this(first, second, reversed, null);
+        }
+
+        public CombineRule(PropertyMatcher first, PropertyMatcher second, boolean reversed, String shortProperty) {
             this.first = first;
             this.second = second;
             this.reversed = reversed;
+            this.shortProperty = shortProperty;
         }
 
         public boolean isReversed() {
@@ -190,5 +213,9 @@
         public PropertyMatcher getSecondMatcher() {
             return second;
         }
+
+        public String getShortProperty() {
+            return shortProperty;
+        }
     }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/ConnectionFilter.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/ConnectionFilter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,12 +23,8 @@
  */
 package com.sun.hotspot.igv.filter;
 
-import com.sun.hotspot.igv.graph.Connection;
-import com.sun.hotspot.igv.graph.Diagram;
-import com.sun.hotspot.igv.graph.Figure;
-import com.sun.hotspot.igv.graph.OutputSlot;
-import com.sun.hotspot.igv.graph.Selector;
 import com.sun.hotspot.igv.data.Properties;
+import com.sun.hotspot.igv.graph.*;
 import java.awt.Color;
 import java.util.ArrayList;
 import java.util.List;
@@ -44,16 +40,18 @@
 
     public ConnectionFilter(String name) {
         this.name = name;
-        connectionStyleRules = new ArrayList<ConnectionStyleRule>();
+        connectionStyleRules = new ArrayList<>();
     }
 
+    @Override
     public String getName() {
         return name;
     }
 
+    @Override
     public void apply(Diagram diagram) {
 
-        Properties.PropertySelector<Figure> selector = new Properties.PropertySelector<Figure>(diagram.getFigures());
+        Properties.PropertySelector<Figure> selector = new Properties.PropertySelector<>(diagram.getFigures());
         for (ConnectionStyleRule rule : connectionStyleRules) {
             List<Figure> figures = null;
             if (rule.getSelector() != null) {
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/CustomFilter.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/CustomFilter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2008, 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
@@ -29,17 +29,13 @@
 import java.io.IOException;
 import java.io.InputStream;
 import java.io.InputStreamReader;
-import java.util.Collection;
 import java.util.logging.Level;
 import java.util.logging.Logger;
-import org.openide.DialogDisplayer;
-import org.openide.NotifyDescriptor;
+import javax.script.*;
 import org.openide.cookies.OpenCookie;
-import org.openide.filesystems.Repository;
-import org.openide.filesystems.FileSystem;
 import org.openide.filesystems.FileObject;
+import org.openide.filesystems.FileUtil;
 import org.openide.util.Exceptions;
-import org.openide.util.Lookup;
 
 /**
  *
@@ -48,7 +44,6 @@
 public class CustomFilter extends AbstractFilter {
 
     public static final String JAVASCRIPT_HELPER_ID = "JavaScriptHelper";
-    private static ScriptEngineAbstraction engine;
     private String code;
     private String name;
 
@@ -58,6 +53,7 @@
         getProperties().setProperty("name", name);
     }
 
+    @Override
     public String getName() {
         return name;
     }
@@ -80,6 +76,7 @@
     public OpenCookie getEditor() {
         return new OpenCookie() {
 
+            @Override
             public void open() {
                 openInEditor();
             }
@@ -89,7 +86,9 @@
     public boolean openInEditor() {
         EditFilterDialog dialog = new EditFilterDialog(CustomFilter.this);
         dialog.setVisible(true);
-        return dialog.wasAccepted();
+        boolean result = dialog.wasAccepted();
+        this.getChangedEvent().fire();
+        return result;
     }
 
     @Override
@@ -97,41 +96,16 @@
         return getName();
     }
 
-    public static ScriptEngineAbstraction getEngine() {
-        if (engine == null) {
-
-            ScriptEngineAbstraction chosen = null;
-            try {
-                Collection<? extends ScriptEngineAbstraction> list = Lookup.getDefault().lookupAll(ScriptEngineAbstraction.class);
-                for (ScriptEngineAbstraction s : list) {
-                    if (s.initialize(getJsHelperText())) {
-                        if (chosen == null || !(chosen instanceof JavaSE6ScriptEngine)) {
-                            chosen = s;
-                        }
-                    }
-                }
-            } catch (NoClassDefFoundError ncdfe) {
-                Logger.getLogger("global").log(Level.SEVERE, null, ncdfe);
-            }
-
-            if (chosen == null) {
-                NotifyDescriptor message = new NotifyDescriptor.Message("Could not find a scripting engine. Please make sure that the Rhino scripting engine is available. Otherwise filter cannot be used.", NotifyDescriptor.ERROR_MESSAGE);
-                DialogDisplayer.getDefault().notifyLater(message);
-                chosen = new NullScriptEngine();
-            }
-
-            engine = chosen;
-        }
-
-        return engine;
-    }
-
     private static String getJsHelperText() {
         InputStream is = null;
-        StringBuilder sb = new StringBuilder("importPackage(Packages.com.sun.hotspot.igv.filter);importPackage(Packages.com.sun.hotspot.igv.graph);importPackage(Packages.com.sun.hotspot.igv.data);importPackage(Packages.com.sun.hotspot.igv.util);importPackage(java.awt);");
+        StringBuilder sb = new StringBuilder("if (typeof importPackage === 'undefined') { try { load('nashorn:mozilla_compat.js'); } catch (e) {} }"
+                + "importPackage(Packages.com.sun.hotspot.igv.filter);"
+                + "importPackage(Packages.com.sun.hotspot.igv.graph);"
+                + "importPackage(Packages.com.sun.hotspot.igv.data);"
+                + "importPackage(Packages.com.sun.hotspot.igv.util);"
+                + "importPackage(java.awt);");
         try {
-            FileSystem fs = Repository.getDefault().getDefaultFileSystem();
-            FileObject fo = fs.getRoot().getFileObject(JAVASCRIPT_HELPER_ID);
+            FileObject fo = FileUtil.getConfigRoot().getFileObject(JAVASCRIPT_HELPER_ID);
             is = fo.getInputStream();
             BufferedReader r = new BufferedReader(new InputStreamReader(is));
             String s;
@@ -152,7 +126,18 @@
         return sb.toString();
     }
 
+    @Override
     public void apply(Diagram d) {
-        getEngine().execute(d, code);
+        try {
+            ScriptEngineManager sem = new ScriptEngineManager();
+            ScriptEngine e = sem.getEngineByName("ECMAScript");
+            e.eval(getJsHelperText());
+            Bindings b = e.getContext().getBindings(ScriptContext.ENGINE_SCOPE);
+            b.put("graph", d);
+            b.put("IO", System.out);
+            e.eval(code, b);
+        } catch (ScriptException ex) {
+            Exceptions.printStackTrace(ex);
+        }
     }
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/EdgeColorIndexFilter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,77 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+package com.sun.hotspot.igv.filter;
+
+import com.sun.hotspot.igv.graph.*;
+import java.awt.Color;
+import java.util.List;
+
+public class EdgeColorIndexFilter extends AbstractFilter {
+
+    public static final String INPUTS = "INPUTS";
+    public static final String OUTPUTS = "OUTPUTS";
+    private final String applyTo;
+    private final Color[] colors;
+
+    public EdgeColorIndexFilter(String applyTo, Color... color) {
+        if (!applyTo.equals(INPUTS) && !applyTo.equals(OUTPUTS)) {
+            throw new IllegalArgumentException("applyTo");
+        }
+
+        this.applyTo = applyTo;
+        this.colors = color;
+    }
+
+    @Override
+    public String getName() {
+        return "Edge Color Index Filter";
+    }
+
+    @Override
+    public void apply(Diagram d) {
+        List<Figure> figures = d.getFigures();
+        for (Figure f : figures) {
+            Slot[] slots;
+            if (applyTo.equals(INPUTS)) {
+                List<InputSlot> inputSlots = f.getInputSlots();
+                slots = inputSlots.toArray(new Slot[inputSlots.size()]);
+            } else {
+                List<OutputSlot> outputSlots = f.getOutputSlots();
+                slots = outputSlots.toArray(new Slot[outputSlots.size()]);
+            }
+            int index = 0;
+            for (Slot slot : slots) {
+                if (index < colors.length && colors[index] != null) {
+                    slot.setColor(colors[index]);
+                    for (Connection c : slot.getConnections()) {
+
+                        c.setColor(colors[index]);
+                    }
+                }
+                index++;
+            }
+
+        }
+    }
+}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/EditFilterDialog.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/EditFilterDialog.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2007, 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,14 +137,14 @@
     }// </editor-fold>//GEN-END:initComponents
 
 private void okButtonClicked(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_okButtonClicked
-        this.customFilter.setName(this.nameTextField.getText());
-        this.customFilter.setCode(this.sourceTextArea.getText());
-        accepted = true;
-        setVisible(false);
+    this.customFilter.setName(this.nameTextField.getText());
+    this.customFilter.setCode(this.sourceTextArea.getText());
+    accepted = true;
+    setVisible(false);
 }//GEN-LAST:event_okButtonClicked
 
 private void cancelButtonClicked(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_cancelButtonClicked
-        setVisible(false);
+    setVisible(false);
 }//GEN-LAST:event_cancelButtonClicked
 
 
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/Filter.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/Filter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -41,5 +41,6 @@
 
     OpenCookie getEditor();
 
+    @Override
     ChangedEvent<Filter> getChangedEvent();
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/FilterChain.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/FilterChain.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,9 +23,10 @@
  */
 package com.sun.hotspot.igv.filter;
 
-import com.sun.hotspot.igv.graph.Diagram;
 import com.sun.hotspot.igv.data.ChangedEvent;
 import com.sun.hotspot.igv.data.ChangedEventProvider;
+import com.sun.hotspot.igv.data.ChangedListener;
+import com.sun.hotspot.igv.graph.Diagram;
 import java.util.ArrayList;
 import java.util.Collections;
 import java.util.List;
@@ -38,20 +39,25 @@
 
     private List<Filter> filters;
     private transient ChangedEvent<FilterChain> changedEvent;
-    private boolean fireEvents;
+
+    private ChangedListener<Filter> changedListener = new ChangedListener<Filter>() {
+        @Override
+        public void changed(Filter source) {
+            changedEvent.fire();
+        }
+    };
 
     public FilterChain() {
-        filters = new ArrayList<Filter>();
-        changedEvent = new ChangedEvent<FilterChain>(this);
-        this.fireEvents = true;
+        filters = new ArrayList<>();
+        changedEvent = new ChangedEvent<>(this);
     }
 
     public FilterChain(FilterChain f) {
-        this.filters = new ArrayList<Filter>(f.filters);
-        changedEvent = new ChangedEvent<FilterChain>(this);
-        this.fireEvents = true;
+        this.filters = new ArrayList<>(f.filters);
+        changedEvent = new ChangedEvent<>(this);
     }
 
+    @Override
     public ChangedEvent<FilterChain> getChangedEvent() {
         return changedEvent;
     }
@@ -68,7 +74,7 @@
     }
 
     public void apply(Diagram d, FilterChain sequence) {
-        List<Filter> applied = new ArrayList<Filter>();
+        List<Filter> applied = new ArrayList<>();
         for (Filter f : sequence.getFilters()) {
             if (filters.contains(f)) {
                 f.apply(d);
@@ -84,29 +90,12 @@
         }
     }
 
-    public void beginAtomic() {
-        this.fireEvents = false;
-    }
-
-    public void endAtomic() {
-        this.fireEvents = true;
-        changedEvent.fire();
-    }
 
     public void addFilter(Filter filter) {
         assert filter != null;
         filters.add(filter);
-        if (fireEvents) {
-            changedEvent.fire();
-        }
-    }
-
-    public void addFilterSameSequence(Filter filter) {
-        assert filter != null;
-        filters.add(filter);
-        if (fireEvents) {
-            changedEvent.fire();
-        }
+        filter.getChangedEvent().addListener(changedListener);
+        changedEvent.fire();
     }
 
     public boolean containsFilter(Filter filter) {
@@ -116,9 +105,8 @@
     public void removeFilter(Filter filter) {
         assert filters.contains(filter);
         filters.remove(filter);
-        if (fireEvents) {
-            changedEvent.fire();
-        }
+        filter.getChangedEvent().removeListener(changedListener);
+        changedEvent.fire();
     }
 
     public void moveFilterUp(Filter filter) {
@@ -128,9 +116,7 @@
             filters.remove(index);
             filters.add(index - 1, filter);
         }
-        if (fireEvents) {
-            changedEvent.fire();
-        }
+        changedEvent.fire();
     }
 
     public void moveFilterDown(Filter filter) {
@@ -140,16 +126,10 @@
             filters.remove(index);
             filters.add(index + 1, filter);
         }
-        if (fireEvents) {
-            changedEvent.fire();
-        }
+        changedEvent.fire();
     }
 
     public List<Filter> getFilters() {
         return Collections.unmodifiableList(filters);
     }
-
-    public void clear() {
-        filters.clear();
-    }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/FilterChainProvider.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/FilterChainProvider.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/FilterSetting.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/FilterSetting.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -42,7 +42,7 @@
 
     public FilterSetting(String name) {
         this.name = name;
-        filters = new HashSet<Filter>();
+        filters = new HashSet<>();
     }
 
     public Set<Filter> getFilters() {
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/GradientColorFilter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,161 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+package com.sun.hotspot.igv.filter;
+
+import com.sun.hotspot.igv.graph.Diagram;
+import com.sun.hotspot.igv.graph.Figure;
+import java.awt.*;
+import java.awt.geom.AffineTransform;
+import java.awt.image.Raster;
+import java.util.List;
+
+/**
+ * Filter that colors nodes using a customizable color gradient, based on how
+ * a numeric property is located in a specified interval.
+ *
+ * @author Peter Hofer
+ */
+public class GradientColorFilter extends AbstractFilter {
+
+    public static final String LINEAR = "LINEAR";
+    public static final String LOGARITHMIC = "LOGARITHMIC";
+
+    private String propertyName = "probability";
+    private float minValue = 0;
+    private float maxValue = 500;
+    private float[] fractions = {0, 0.5f, 1};
+    private Color[] colors = {Color.BLUE, Color.YELLOW, Color.RED};
+    private int shadeCount = 8;
+    private String mode = LINEAR;
+
+    @Override
+    public String getName() {
+        return "Gradient Color Filter";
+    }
+
+    @Override
+    public void apply(Diagram d) {
+        boolean logarithmic = mode.equalsIgnoreCase(LOGARITHMIC);
+        if (!logarithmic && !mode.equalsIgnoreCase(LINEAR)) {
+            throw new RuntimeException("Unknown mode: " + mode);
+        }
+
+        Rectangle bounds = new Rectangle(shadeCount, 1);
+        LinearGradientPaint lgp = new LinearGradientPaint(bounds.x, bounds.y, bounds.width, bounds.y, fractions, colors);
+        PaintContext context = lgp.createContext(null, bounds, bounds.getBounds2D(), AffineTransform.getTranslateInstance(0, 0), new RenderingHints(null));
+        Raster raster = context.getRaster(bounds.x, bounds.y, bounds.width, bounds.height);
+        int[] rgb = raster.getPixels(bounds.x, bounds.y, bounds.width, bounds.height, (int[]) null);
+        Color[] shades = new Color[rgb.length / 3];
+        for (int i = 0; i < shades.length; ++i) {
+            shades[i] = new Color(rgb[i * 3], rgb[i * 3 + 1], rgb[i * 3 + 2]);
+        }
+
+        List<Figure> figures = d.getFigures();
+        for (Figure f : figures) {
+            String property = f.getProperties().get(propertyName);
+            if (property != null) {
+                try {
+                    float value = Float.parseFloat(property);
+
+                    Color nodeColor;
+                    if (value <= minValue) {
+                        nodeColor = colors[0];
+                    } else if (value >= maxValue) {
+                        nodeColor = colors[colors.length - 1];
+                    } else {
+                        double normalized = value - minValue;
+                        double interval = maxValue - minValue;
+                        int index;
+                        // Use Math.ceil() to make values above zero distinguishable from zero
+                        if (logarithmic) {
+                            index = (int) Math.ceil(shades.length * Math.log(1 + normalized) / Math.log(1 + interval));
+                        } else {
+                            index = (int) Math.ceil(shades.length * normalized / interval);
+                        }
+                        nodeColor = shades[index];
+                    }
+                    f.setColor(nodeColor);
+                } catch (Exception e) {
+                    e.printStackTrace();
+                }
+            }
+        }
+    }
+
+    public String getPropertyName() {
+        return propertyName;
+    }
+
+    public void setPropertyName(String propertyName) {
+        this.propertyName = propertyName;
+    }
+
+    public float getMinValue() {
+        return minValue;
+    }
+
+    public void setMinValue(float minValue) {
+        this.minValue = minValue;
+    }
+
+    public float getMaxValue() {
+        return maxValue;
+    }
+
+    public void setMaxValue(float maxValue) {
+        this.maxValue = maxValue;
+    }
+
+    public float[] getFractions() {
+        return fractions;
+    }
+
+    public void setFractions(float[] fractions) {
+        this.fractions = fractions;
+    }
+
+    public Color[] getColors() {
+        return colors;
+    }
+
+    public void setColors(Color[] colors) {
+        this.colors = colors;
+    }
+
+    public int getShadeCount() {
+        return shadeCount;
+    }
+
+    public void setShadeCount(int shadeCount) {
+        this.shadeCount = shadeCount;
+    }
+
+    public String getMode() {
+        return mode;
+    }
+
+    public void setMode(String mode) {
+        this.mode = mode;
+    }
+}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/JavaSE6ScriptEngine.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,68 +0,0 @@
-/*
- * Copyright (c) 1998, 2007, Oracle and/or its affiliates. All rights reserved.
- * 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 com.sun.hotspot.igv.filter;
-
-import com.sun.hotspot.igv.graph.Diagram;
-import javax.script.Bindings;
-import javax.script.ScriptContext;
-import javax.script.ScriptEngine;
-import javax.script.ScriptEngineManager;
-import javax.script.ScriptException;
-import org.openide.util.Exceptions;
-
-/**
- *
- * @author Thomas Wuerthinger
- */
-public class JavaSE6ScriptEngine implements ScriptEngineAbstraction {
-
-    private ScriptEngine engine;
-    private Bindings bindings;
-
-    public boolean initialize(String jsHelperText) {
-        try {
-            ScriptEngineManager sem = new ScriptEngineManager();
-            ScriptEngine e = sem.getEngineByName("ECMAScript");
-            engine = e;
-            e.eval(jsHelperText);
-            Bindings b = e.getContext().getBindings(ScriptContext.ENGINE_SCOPE);
-            b.put("IO", System.out);
-            bindings = b;
-            return true;
-        } catch (Exception e) {
-            return false;
-        }
-    }
-
-    public void execute(Diagram d, String code) {
-        try {
-            Bindings b = bindings;
-            b.put("graph", d);
-            engine.eval(code, b);
-        } catch (ScriptException ex) {
-            Exceptions.printStackTrace(ex);
-        }
-    }
-}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/NullScriptEngine.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,40 +0,0 @@
-/*
- * Copyright (c) 2008, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- *
- */
-package com.sun.hotspot.igv.filter;
-
-import com.sun.hotspot.igv.graph.Diagram;
-
-/**
- *
- * @author Thomas Wuerthinger
- */
-public class NullScriptEngine implements ScriptEngineAbstraction {
-
-    public boolean initialize(String jsHelperText) {
-        return true;
-    }
-
-    public void execute(Diagram d, String code) {
-    }
-}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/RemoveFilter.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/RemoveFilter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -25,9 +25,7 @@
 
 import com.sun.hotspot.igv.graph.Diagram;
 import com.sun.hotspot.igv.graph.Figure;
-import com.sun.hotspot.igv.graph.InputSlot;
 import com.sun.hotspot.igv.graph.Selector;
-import com.sun.hotspot.igv.data.Properties;
 import java.util.ArrayList;
 import java.util.HashSet;
 import java.util.List;
@@ -44,56 +42,36 @@
 
     public RemoveFilter(String name) {
         this.name = name;
-        rules = new ArrayList<RemoveRule>();
+        rules = new ArrayList<>();
     }
 
+    @Override
     public String getName() {
         return name;
     }
 
+    @Override
     public void apply(Diagram diagram) {
-
         for (RemoveRule r : rules) {
+            List<Figure> selected = r.getSelector().selected(diagram);
+            Set<Figure> toRemove = new HashSet<>(selected);
 
-            List<Figure> list = r.getSelector().selected(diagram);
-            Set<Figure> figuresToRemove = new HashSet<Figure>();
-
-            List<Figure> protectedFigures = null;
-            if (r.getRemoveAllWithoutPredecessor()) {
-                protectedFigures = diagram.getRootFigures();
+            if (r.getRemoveOrphans()) {
+                boolean changed;
+                do {
+                    changed = false;
+                    for (Figure f : diagram.getFigures()) {
+                        if (!toRemove.contains(f)) {
+                            if (toRemove.containsAll(f.getPredecessors()) && toRemove.containsAll(f.getSuccessors())) {
+                                toRemove.add(f);
+                                changed = true;
+                            }
+                        }
+                    }
+                } while (changed);
             }
 
-            for (Figure f : list) {
-                if (r.getRemoveOnlyInputs()) {
-                    List<InputSlot> inputSlots = new ArrayList<InputSlot>();
-                    for (InputSlot is : f.getInputSlots()) {
-                        inputSlots.add(is);
-                    }
-                    for (InputSlot is : inputSlots) {
-                        f.removeSlot(is);
-                    }
-
-                    f.createInputSlot();
-                } else {
-                    figuresToRemove.add(f);
-                }
-            }
-
-            if (r.getRemoveAllWithoutPredecessor()) {
-                boolean progress = true;
-                while (progress) {
-                    List<Figure> rootFigures = diagram.getRootFigures();
-                    progress = false;
-                    for (Figure f : rootFigures) {
-                        if (!protectedFigures.contains(f)) {
-                            figuresToRemove.add(f);
-                            progress = true;
-                        }
-                    }
-                }
-            }
-
-            diagram.removeAllFigures(figuresToRemove);
+            diagram.removeAllFigures(toRemove);
         }
     }
 
@@ -104,29 +82,23 @@
     public static class RemoveRule {
 
         private Selector selector;
-        private boolean removeAllWithoutPredecessor;
-        private boolean removeOnlyInputs;
+        private boolean removeOrphans;
 
-        public RemoveRule(Selector selector, boolean b) {
-            this(selector, b, false);
+        public RemoveRule(Selector selector) {
+            this(selector, false);
         }
 
-        public RemoveRule(Selector selector, boolean removeAllWithoutPredecessor, boolean removeOnlyInputs) {
+        public RemoveRule(Selector selector, boolean removeOrphans) {
             this.selector = selector;
-            this.removeOnlyInputs = removeOnlyInputs;
-            this.removeAllWithoutPredecessor = removeAllWithoutPredecessor;
+            this.removeOrphans = removeOrphans;
         }
 
         public Selector getSelector() {
             return selector;
         }
 
-        public boolean getRemoveOnlyInputs() {
-            return removeOnlyInputs;
-        }
-
-        public boolean getRemoveAllWithoutPredecessor() {
-            return removeAllWithoutPredecessor;
+        public boolean getRemoveOrphans() {
+            return removeOrphans;
         }
     }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/RemoveInputsFilter.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/RemoveInputsFilter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,12 +23,7 @@
  */
 package com.sun.hotspot.igv.filter;
 
-import com.sun.hotspot.igv.graph.Connection;
-import com.sun.hotspot.igv.graph.Diagram;
-import com.sun.hotspot.igv.graph.Figure;
-import com.sun.hotspot.igv.graph.InputSlot;
-import com.sun.hotspot.igv.graph.OutputSlot;
-import com.sun.hotspot.igv.graph.Selector;
+import com.sun.hotspot.igv.graph.*;
 import java.util.ArrayList;
 import java.util.List;
 
@@ -43,13 +38,15 @@
 
     public RemoveInputsFilter(String name) {
         this.name = name;
-        rules = new ArrayList<RemoveInputsRule>();
+        rules = new ArrayList<>();
     }
 
+    @Override
     public String getName() {
         return name;
     }
 
+    @Override
     public void apply(Diagram diagram) {
 
         for (RemoveInputsRule r : rules) {
@@ -57,7 +54,7 @@
             List<Figure> list = r.getSelector().selected(diagram);
             for (Figure f : list) {
                 int z = 0;
-                List<InputSlot> last = new ArrayList<InputSlot>();
+                List<InputSlot> last = new ArrayList<>();
                 for (InputSlot is : f.getInputSlots()) {
                     if (z >= r.getStartingIndex() && z <= r.getEndIndex() && is.getConnections().size() > 0) {
                         StringBuilder sb = new StringBuilder();
@@ -73,7 +70,7 @@
                         }
                         is.removeAllConnections();
                         is.setShortName("X");
-                        is.setName(sb.toString());
+                        is.setText(sb.toString());
                         last.add(is);
                     } else {
                         last.clear();
@@ -91,10 +88,10 @@
                         if (i != 0) {
                             sb.append("<BR>");
                         }
-                        sb.append(is2.getName());
+                        sb.append(is2.getText());
                     }
 
-                    first.setName(sb.toString());
+                    first.setText(sb.toString());
 
                     for (int i = 1; i < last.size(); i++) {
                         f.removeSlot(last.get(i));
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/RemoveSelfLoopsFilter.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/RemoveSelfLoopsFilter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,11 +23,7 @@
  */
 package com.sun.hotspot.igv.filter;
 
-import com.sun.hotspot.igv.graph.Connection;
-import com.sun.hotspot.igv.graph.Diagram;
-import com.sun.hotspot.igv.graph.Figure;
-import com.sun.hotspot.igv.graph.InputSlot;
-import com.sun.hotspot.igv.graph.OutputSlot;
+import com.sun.hotspot.igv.graph.*;
 import java.util.ArrayList;
 import java.util.List;
 
@@ -44,17 +40,19 @@
         this.name = name;
     }
 
+    @Override
     public String getName() {
         return name;
     }
 
+    @Override
     public void apply(Diagram d) {
 
         for (Figure f : d.getFigures()) {
 
             for (InputSlot is : f.getInputSlots()) {
 
-                List<Connection> toRemove = new ArrayList<Connection>();
+                List<Connection> toRemove = new ArrayList<>();
                 for (Connection c : is.getConnections()) {
 
                     if (c.getOutputSlot().getFigure() == f) {
@@ -72,7 +70,7 @@
                     }
 
                     c.getInputSlot().setShortName("O");
-                    c.getInputSlot().setName("Self Loop");
+                    c.getInputSlot().setText("Self Loop");
                 }
             }
         }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/ScriptEngineAbstraction.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,38 +0,0 @@
-/*
- * Copyright (c) 1998, 2007, Oracle and/or its affiliates. All rights reserved.
- * 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 com.sun.hotspot.igv.filter;
-
-import com.sun.hotspot.igv.graph.Diagram;
-
-/**
- *
- * @author Thomas Wuerthinger
- */
-public interface ScriptEngineAbstraction {
-
-    public boolean initialize(String jsHelperText);
-
-    public void execute(Diagram d, String code);
-}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/SplitFilter.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/SplitFilter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,12 +23,7 @@
  */
 package com.sun.hotspot.igv.filter;
 
-import com.sun.hotspot.igv.graph.Connection;
-import com.sun.hotspot.igv.graph.Diagram;
-import com.sun.hotspot.igv.graph.Figure;
-import com.sun.hotspot.igv.graph.InputSlot;
-import com.sun.hotspot.igv.graph.OutputSlot;
-import com.sun.hotspot.igv.graph.Selector;
+import com.sun.hotspot.igv.graph.*;
 import java.util.List;
 
 /**
@@ -39,25 +34,52 @@
 
     private String name;
     private Selector selector;
+    private String propertyName;
 
-    public SplitFilter(String name, Selector selector) {
+    public SplitFilter(String name, Selector selector, String propertyName) {
         this.name = name;
         this.selector = selector;
+        this.propertyName = propertyName;
     }
 
+    @Override
     public String getName() {
         return name;
     }
 
+    @Override
     public void apply(Diagram d) {
         List<Figure> list = selector.selected(d);
 
         for (Figure f : list) {
+
+            for (InputSlot is : f.getInputSlots()) {
+                for (Connection c : is.getConnections()) {
+                    OutputSlot os = c.getOutputSlot();
+                    if (f.getSource().getSourceNodes().size() > 0) {
+                        os.getSource().addSourceNodes(f.getSource());
+                        os.setAssociatedNode(f.getSource().getSourceNodes().get(0));
+                        os.setColor(f.getColor());
+                    }
+
+
+                    String s = Figure.resolveString(propertyName, f.getProperties());
+                    if (s != null) {
+                        os.setShortName(s);
+                    }
+
+                }
+            }
             for (OutputSlot os : f.getOutputSlots()) {
                 for (Connection c : os.getConnections()) {
                     InputSlot is = c.getInputSlot();
-                    is.setName(f.getProperties().get("dump_spec"));
-                    String s = f.getProperties().get("short_name");
+                    if (f.getSource().getSourceNodes().size() > 0) {
+                        is.getSource().addSourceNodes(f.getSource());
+                        is.setAssociatedNode(f.getSource().getSourceNodes().get(0));
+                        is.setColor(f.getColor());
+                    }
+
+                    String s = Figure.resolveString(propertyName, f.getProperties());
                     if (s != null) {
                         is.setShortName(s);
                     }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/UnconnectedSlotFilter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,76 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+package com.sun.hotspot.igv.filter;
+
+import com.sun.hotspot.igv.graph.*;
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * Filter that hides slots with no connections.
+ */
+public class UnconnectedSlotFilter extends AbstractFilter {
+
+    private final boolean removeInputs;
+    private final boolean removeOutputs;
+
+    public UnconnectedSlotFilter(boolean inputs, boolean outputs) {
+        this.removeInputs = inputs;
+        this.removeOutputs = outputs;
+    }
+
+    @Override
+    public String getName() {
+        return "Unconnected Slot Filter";
+    }
+
+    @Override
+    public void apply(Diagram d) {
+        if (!removeInputs && !removeOutputs) {
+            return;
+        }
+
+        List<Figure> figures = d.getFigures();
+        for (Figure f : figures) {
+            List<Slot> remove = new ArrayList<>();
+            if (removeInputs) {
+                for (InputSlot is : f.getInputSlots()) {
+                    if (is.getConnections().isEmpty()) {
+                        remove.add(is);
+                    }
+                }
+            }
+            if (removeOutputs) {
+                for (OutputSlot os : f.getOutputSlots()) {
+                    if (os.getConnections().isEmpty()) {
+                        remove.add(os);
+                    }
+                }
+            }
+            for (Slot s : remove) {
+                f.removeSlot(s);
+            }
+        }
+    }
+}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/helper.js	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Filter/src/com/sun/hotspot/igv/filter/helper.js	Wed Jul 05 20:35:10 2017 +0200
@@ -21,26 +21,35 @@
  * questions.
  *
  */
-
+ 
  /**
  *
  * @author Thomas Wuerthinger
  */
-
+ 
 function colorize(property, regexp, color) {
     var f = new ColorFilter("");
     f.addRule(new ColorFilter.ColorRule(new MatcherSelector(new Properties.RegexpPropertyMatcher(property, regexp)), color));
-    f.apply(graph);
+    f.apply(graph); 
 }
 
 function remove(property, regexp) {
     var f = new RemoveFilter("");
-    f.addRule(new RemoveFilter.RemoveRule(new MatcherSelector(new Properties.RegexpPropertyMatcher(property, regexp)), false, false));
+    f.addRule(new RemoveFilter.RemoveRule(new MatcherSelector(new Properties.RegexpPropertyMatcher(property, regexp))));
     f.apply(graph);
 }
 
-function split(property, regexp) {
-    var f = new SplitFilter("", new MatcherSelector(new Properties.RegexpPropertyMatcher(property, regexp)));
+function removeIncludingOrphans(property, regexp) {
+    var f = new RemoveFilter("");
+    f.addRule(new RemoveFilter.RemoveRule(new MatcherSelector(new Properties.RegexpPropertyMatcher(property, regexp)), true));
+    f.apply(graph);
+}
+
+function split(property, regexp, propertyName) {
+    if (propertyName == undefined) {
+        propertyName = graph.getNodeText();
+    }
+    var f = new SplitFilter("", new MatcherSelector(new Properties.RegexpPropertyMatcher(property, regexp)), propertyName);
     f.apply(graph);
 }
 
@@ -56,6 +65,40 @@
     f.apply(graph);
 }
 
+function removeUnconnectedSlots(inputs, outputs) {
+    var f = new UnconnectedSlotFilter(inputs, outputs);
+    f.apply(graph);
+}
+
+function colorizeGradient(property, min, max) {
+    var f = new GradientColorFilter();
+    f.setPropertyName(property);
+    f.setMinValue(min);
+    f.setMaxValue(max);
+    f.apply(graph);
+}
+
+function colorizeGradientWithMode(property, min, max, mode) {
+    var f = new GradientColorFilter();
+    f.setPropertyName(property);
+    f.setMinValue(min);
+    f.setMaxValue(max);
+    f.setMode(mode);
+    f.apply(graph);
+}
+
+function colorizeGradientCustom(property, min, max, mode, colors, fractions, nshades) {
+    var f = new GradientColorFilter();
+    f.setPropertyName(property);
+    f.setMinValue(min);
+    f.setMaxValue(max);
+    f.setMode(mode);
+    f.setColors(colors);
+    f.setFractions(fractions);
+    f.setShadeCount(nshades);
+    f.apply(graph);
+}
+
 var black = Color.black;
 var blue = Color.blue;
 var cyan = Color.cyan;
@@ -68,4 +111,4 @@
 var pink = Color.pink
 var red = Color.red;
 var yellow = Color.yellow;
-var white = Color.white;
+var white = Color.white;
\ No newline at end of file
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/nbproject/build-impl.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/nbproject/build-impl.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -4,6 +4,13 @@
 ***         EDIT ../build.xml INSTEAD         ***
 -->
 <project name="com.sun.hotspot.igv.filterwindow-impl" basedir="..">
+    <fail message="Please build using Ant 1.7.1 or higher.">
+        <condition>
+            <not>
+                <antversion atleast="1.7.1"/>
+            </not>
+        </condition>
+    </fail>
     <property file="nbproject/private/suite-private.properties"/>
     <property file="nbproject/suite.properties"/>
     <fail unless="suite.dir">You must set 'suite.dir' to point to your containing module suite</fail>
@@ -16,13 +23,21 @@
             <property name="@{name}" value="${@{value}}"/>
         </sequential>
     </macrodef>
+    <macrodef name="evalprops" uri="http://www.netbeans.org/ns/nb-module-project/2">
+        <attribute name="property"/>
+        <attribute name="value"/>
+        <sequential>
+            <property name="@{property}" value="@{value}"/>
+        </sequential>
+    </macrodef>
     <property file="${user.properties.file}"/>
     <nbmproject2:property name="harness.dir" value="nbplatform.${nbplatform.active}.harness.dir" xmlns:nbmproject2="http://www.netbeans.org/ns/nb-module-project/2"/>
-    <nbmproject2:property name="netbeans.dest.dir" value="nbplatform.${nbplatform.active}.netbeans.dest.dir" xmlns:nbmproject2="http://www.netbeans.org/ns/nb-module-project/2"/>
-    <fail message="You must define 'nbplatform.${nbplatform.active}.harness.dir'">
+    <nbmproject2:property name="nbplatform.active.dir" value="nbplatform.${nbplatform.active}.netbeans.dest.dir" xmlns:nbmproject2="http://www.netbeans.org/ns/nb-module-project/2"/>
+    <nbmproject2:evalprops property="cluster.path.evaluated" value="${cluster.path}" xmlns:nbmproject2="http://www.netbeans.org/ns/nb-module-project/2"/>
+    <fail message="Path to 'platform' cluster missing in $${cluster.path} property or using corrupt Netbeans Platform (missing harness).">
         <condition>
             <not>
-                <available file="${harness.dir}" type="dir"/>
+                <contains string="${cluster.path.evaluated}" substring="platform"/>
             </not>
         </condition>
     </fail>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/nbproject/genfiles.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/nbproject/genfiles.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,8 +1,5 @@
-build.xml.data.CRC32=401b2654
-build.xml.script.CRC32=9c158403
-build.xml.stylesheet.CRC32=79c3b980
 # This file is used by a NetBeans-based IDE to track changes in generated files such as build-impl.xml.
 # Do not edit this file. You may delete it but then the IDE will never regenerate such files for you.
-nbproject/build-impl.xml.data.CRC32=401b2654
-nbproject/build-impl.xml.script.CRC32=19fb08e0
-nbproject/build-impl.xml.stylesheet.CRC32=deb65f65
+nbproject/build-impl.xml.data.CRC32=5b8e8a60
+nbproject/build-impl.xml.script.CRC32=e4293f0e
+nbproject/build-impl.xml.stylesheet.CRC32=238281d1@2.67.1
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/nbproject/project.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/nbproject/project.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,2 +1,2 @@
-javac.source=1.5
-javac.compilerargs=-Xlint -Xlint:-serial
+javac.source=1.7
+javac.compilerargs=-Xlint -Xlint:-serial
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/nbproject/project.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/nbproject/project.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -43,7 +43,15 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>6.6.1.1</specification-version>
+                        <specification-version>6.21.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.awt</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>7.39.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -51,7 +59,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>7.5.1</specification-version>
+                        <specification-version>7.18.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -59,7 +67,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>6.12.1</specification-version>
+                        <specification-version>6.34.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -67,7 +75,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>7.3.1</specification-version>
+                        <specification-version>7.46.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -75,7 +83,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>6.7.1</specification-version>
+                        <specification-version>7.20.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -83,7 +91,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>7.2.1.1</specification-version>
+                        <specification-version>7.20.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -91,7 +99,15 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>7.10.1.1</specification-version>
+                        <specification-version>8.14.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.util.lookup</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>8.6.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -99,7 +115,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>6.18.1</specification-version>
+                        <specification-version>6.39.1</specification-version>
                     </run-dependency>
                 </dependency>
             </module-dependencies>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/Bundle.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/Bundle.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,3 +1,3 @@
 OpenIDE-Module-Name=FilterWindow
-CTL_FilterTopComponent=Filter Window
-HINT_FilterTopComponent=This is a Filter window
+CTL_FilterTopComponent=Filters
+HINT_FilterTopComponent=Allows to choose active filters and modify them.
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/CheckListView.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/CheckListView.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -44,8 +44,8 @@
     }
 
     @Override
-    protected JList createList() {
-        JList tmpList = super.createList();
+    protected JList<Object> createList() {
+        JList<Object> tmpList = super.createList();
         tmpList.setCellRenderer(new CheckRenderer(tmpList));
         return tmpList;
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/CheckNode.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/CheckNode.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -40,7 +40,7 @@
 
     public CheckNode(Children c, Lookup lookup) {
         super(c, lookup);
-        selectionChangedEvent = new ChangedEvent<CheckNode>(this);
+        selectionChangedEvent = new ChangedEvent<>(this);
         selected = false;
         enabled = true;
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/CheckNodeListModel.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/CheckNodeListModel.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -24,7 +24,7 @@
 package com.sun.hotspot.igv.filterwindow;
 
 import org.openide.explorer.view.NodeListModel;
-import org.openide.nodes.Node;
+import org.openide.explorer.view.Visualizer;
 
 /**
  *
@@ -32,15 +32,11 @@
  */
 public class CheckNodeListModel extends NodeListModel {
 
-    private Node rootNode;
-
-    @Override
-    public void setNode(Node rootNode) {
-        this.rootNode = rootNode;
-        super.setNode(rootNode);
-    }
-
     public CheckNode getCheckNodeAt(int index) {
-        return (CheckNode) rootNode.getChildren().getNodes()[index];
+        Object item = getElementAt(index);
+        if (item != null) {
+            return (CheckNode) Visualizer.findNode(item);
+        }
+        return null;
     }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/CheckRenderer.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/CheckRenderer.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,11 +23,7 @@
  */
 package com.sun.hotspot.igv.filterwindow;
 
-import java.awt.Color;
-import java.awt.Component;
-import java.awt.Dimension;
-import java.awt.Point;
-import java.awt.Rectangle;
+import java.awt.*;
 import java.awt.event.MouseAdapter;
 import java.awt.event.MouseEvent;
 import javax.swing.JCheckBox;
@@ -37,12 +33,12 @@
 /**
  * @author Thomas Wuerthinger
  */
-public class CheckRenderer extends JCheckBox implements ListCellRenderer {
+public class CheckRenderer extends JCheckBox implements ListCellRenderer<Object> {
 
-    private JList list;
+    private JList<Object> list;
     private Color startBackground;
 
-    public CheckRenderer(final JList list) {
+    public CheckRenderer(final JList<Object> list) {
         this.list = list;
         list.addMouseListener(
                 new MouseAdapter() {
@@ -65,7 +61,8 @@
         startBackground = this.getBackground();
     }
 
-    public Component getListCellRendererComponent(final JList list, Object value, final int index, boolean isSelected, boolean cellHasFocus) {
+    @Override
+    public Component getListCellRendererComponent(final JList<? extends Object> list, Object value, final int index, boolean isSelected, boolean cellHasFocus) {
         setText(value.toString());
         CheckNode node = ((CheckNodeListModel) list.getModel()).getCheckNodeAt(index);
         this.setSelected(node.isSelected());
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/FilterChainProviderImplementation.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/FilterChainProviderImplementation.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -32,10 +32,12 @@
  */
 public class FilterChainProviderImplementation implements FilterChainProvider {
 
+    @Override
     public FilterChain getFilterChain() {
         return FilterTopComponent.findInstance().getFilterChain();
     }
 
+    @Override
     public FilterChain getSequence() {
         return FilterTopComponent.findInstance().getSequence();
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/FilterNode.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/FilterNode.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,12 +23,12 @@
  */
 package com.sun.hotspot.igv.filterwindow;
 
+import com.sun.hotspot.igv.data.ChangedListener;
+import com.sun.hotspot.igv.filter.Filter;
+import com.sun.hotspot.igv.filter.FilterChain;
 import com.sun.hotspot.igv.filterwindow.actions.MoveFilterDownAction;
 import com.sun.hotspot.igv.filterwindow.actions.MoveFilterUpAction;
 import com.sun.hotspot.igv.filterwindow.actions.RemoveFilterAction;
-import com.sun.hotspot.igv.filter.Filter;
-import com.sun.hotspot.igv.filter.FilterChain;
-import com.sun.hotspot.igv.data.ChangedListener;
 import com.sun.hotspot.igv.util.PropertiesSheet;
 import javax.swing.Action;
 import org.openide.actions.OpenAction;
@@ -48,7 +48,7 @@
 public class FilterNode extends CheckNode implements LookupListener, ChangedListener<FilterTopComponent> {
 
     private Filter filter;
-    private Lookup.Result result;
+    private Lookup.Result<FilterChain> result;
 
     public FilterNode(Filter filter) {
         this(filter, new InstanceContent());
@@ -62,6 +62,7 @@
         this.filter = filter;
         filter.getChangedEvent().addListener(new ChangedListener<Filter>() {
 
+            @Override
             public void changed(Filter source) {
                 update();
             }
@@ -69,12 +70,14 @@
 
         update();
 
-        Lookup.Template<FilterChain> tpl = new Lookup.Template<FilterChain>(FilterChain.class);
+        Lookup.Template<FilterChain> tpl = new Lookup.Template<>(FilterChain.class);
         result = Utilities.actionsGlobalContext().lookup(tpl);
         result.addLookupListener(this);
 
         FilterTopComponent.findInstance().getFilterSettingsChangedEvent().addListener(this);
         resultChanged(null);
+
+        setShortDescription("Double-click to open filter");
     }
 
     private void update() {
@@ -102,10 +105,12 @@
         return OpenAction.get(OpenAction.class).createContextAwareInstance(Utilities.actionsGlobalContext());
     }
 
+    @Override
     public void resultChanged(LookupEvent lookupEvent) {
         changed(FilterTopComponent.findInstance());
     }
 
+    @Override
     public void changed(FilterTopComponent source) {
         setSelected(source.getFilterChain().containsFilter(filter));
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/FilterTopComponent.form	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/FilterTopComponent.form	Wed Jul 05 20:35:10 2017 +0200
@@ -3,6 +3,8 @@
 <Form version="1.2" maxVersion="1.2" type="org.netbeans.modules.form.forminfo.JPanelFormInfo">
   <AuxValues>
     <AuxValue name="FormSettings_autoResourcing" type="java.lang.Integer" value="0"/>
+    <AuxValue name="FormSettings_autoSetComponentName" type="java.lang.Boolean" value="false"/>
+    <AuxValue name="FormSettings_generateFQN" type="java.lang.Boolean" value="true"/>
     <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="true"/>
     <AuxValue name="FormSettings_i18nAutoMode" type="java.lang.Boolean" value="false"/>
     <AuxValue name="FormSettings_layoutCodeTarget" type="java.lang.Integer" value="2"/>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/FilterTopComponent.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/FilterTopComponent.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,65 +23,38 @@
  */
 package com.sun.hotspot.igv.filterwindow;
 
-import com.sun.hotspot.igv.filterwindow.actions.MoveFilterDownAction;
-import com.sun.hotspot.igv.filterwindow.actions.MoveFilterUpAction;
-import com.sun.hotspot.igv.filterwindow.actions.NewFilterAction;
-import com.sun.hotspot.igv.filterwindow.actions.RemoveFilterAction;
-import com.sun.hotspot.igv.filterwindow.actions.RemoveFilterSettingsAction;
-import com.sun.hotspot.igv.filterwindow.actions.SaveFilterSettingsAction;
+import com.sun.hotspot.igv.data.ChangedEvent;
+import com.sun.hotspot.igv.data.ChangedListener;
 import com.sun.hotspot.igv.filter.CustomFilter;
 import com.sun.hotspot.igv.filter.Filter;
 import com.sun.hotspot.igv.filter.FilterChain;
 import com.sun.hotspot.igv.filter.FilterSetting;
-import com.sun.hotspot.igv.data.ChangedEvent;
-import com.sun.hotspot.igv.data.ChangedListener;
+import com.sun.hotspot.igv.filterwindow.actions.*;
 import java.awt.BorderLayout;
 import java.awt.event.ActionEvent;
 import java.awt.event.ActionListener;
-import java.io.BufferedReader;
-import java.io.FileNotFoundException;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.InputStreamReader;
-import java.io.ObjectInput;
-import java.io.ObjectOutput;
-import java.io.OutputStream;
-import java.io.OutputStreamWriter;
-import java.io.Serializable;
-import java.io.Writer;
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.Comparator;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Set;
+import java.io.*;
+import java.util.*;
 import javax.swing.JComboBox;
 import javax.swing.UIManager;
 import javax.swing.border.Border;
 import org.openide.DialogDisplayer;
 import org.openide.ErrorManager;
 import org.openide.NotifyDescriptor;
+import org.openide.awt.Toolbar;
 import org.openide.awt.ToolbarPool;
 import org.openide.explorer.ExplorerManager;
 import org.openide.explorer.ExplorerUtils;
+import org.openide.filesystems.FileLock;
+import org.openide.filesystems.FileObject;
+import org.openide.filesystems.FileUtil;
 import org.openide.nodes.AbstractNode;
 import org.openide.nodes.Children;
 import org.openide.nodes.Node;
-import org.openide.util.Exceptions;
-import org.openide.util.Lookup;
-import org.openide.util.LookupEvent;
-import org.openide.util.LookupListener;
-import org.openide.util.NbBundle;
-import org.openide.util.Utilities;
-import org.openide.awt.Toolbar;
-import org.openide.filesystems.FileLock;
+import org.openide.util.*;
 import org.openide.util.actions.SystemAction;
 import org.openide.windows.TopComponent;
 import org.openide.windows.WindowManager;
-import org.openide.filesystems.Repository;
-import org.openide.filesystems.FileSystem;
-import org.openide.filesystems.FileObject;
 
 /**
  *
@@ -98,13 +71,14 @@
     private ExplorerManager manager;
     private FilterChain filterChain;
     private FilterChain sequence;
-    private Lookup.Result result;
+    private Lookup.Result<FilterChain> result;
     private JComboBox comboBox;
     private List<FilterSetting> filterSettings;
     private FilterSetting customFilterSetting = new FilterSetting("-- Custom --");
     private ChangedEvent<FilterTopComponent> filterSettingsChangedEvent;
     private ActionListener comboBoxActionListener = new ActionListener() {
 
+        @Override
         public void actionPerformed(ActionEvent e) {
             comboBoxSelectionChanged();
         }
@@ -139,8 +113,8 @@
 
         if (s != customFilterSetting) {
             FilterChain chain = getFilterChain();
-            chain.beginAtomic();
-            List<Filter> toRemove = new ArrayList<Filter>();
+            chain.getChangedEvent().beginAtomic();
+            List<Filter> toRemove = new ArrayList<>();
             for (Filter f : chain.getFilters()) {
                 if (!s.containsFilter(f)) {
                     toRemove.add(f);
@@ -156,7 +130,7 @@
                 }
             }
 
-            chain.endAtomic();
+            chain.getChangedEvent().endAtomic();
             filterSettingsChangedEvent.fire();
         } else {
             this.updateComboBoxSelection();
@@ -177,14 +151,14 @@
     }
 
     public void addFilterSetting() {
-        NotifyDescriptor.InputLine l = new NotifyDescriptor.InputLine("Enter a name:", "Filter");
+        NotifyDescriptor.InputLine l = new NotifyDescriptor.InputLine("Name of the new profile:", "Filter Profile");
         if (DialogDisplayer.getDefault().notify(l) == NotifyDescriptor.OK_OPTION) {
             String name = l.getInputText();
 
             FilterSetting toRemove = null;
             for (FilterSetting s : filterSettings) {
                 if (s.getName().equals(name)) {
-                    NotifyDescriptor.Confirmation conf = new NotifyDescriptor.Confirmation("Filter \"" + name + "\" already exists, to you want to overwrite?", "Filter");
+                    NotifyDescriptor.Confirmation conf = new NotifyDescriptor.Confirmation("Filter profile \"" + name + "\" already exists, do you want to replace it?", "Filter");
                     if (DialogDisplayer.getDefault().notify(conf) == NotifyDescriptor.YES_OPTION) {
                         toRemove = s;
                         break;
@@ -203,6 +177,7 @@
             // Sort alphabetically
             Collections.sort(filterSettings, new Comparator<FilterSetting>() {
 
+                @Override
                 public int compare(FilterSetting o1, FilterSetting o2) {
                     return o1.getName().compareTo(o2.getName());
                 }
@@ -223,7 +198,7 @@
             FilterSetting f = (FilterSetting) o;
             assert f != customFilterSetting;
             assert filterSettings.contains(f);
-            NotifyDescriptor.Confirmation l = new NotifyDescriptor.Confirmation("Do you really want to remove filter \"" + f + "\"?", "Filter");
+            NotifyDescriptor.Confirmation l = new NotifyDescriptor.Confirmation("Do you really want to remove filter profile \"" + f + "\"?", "Filter Profile");
             if (DialogDisplayer.getDefault().notify(l) == NotifyDescriptor.YES_OPTION) {
                 filterSettings.remove(f);
                 updateComboBox();
@@ -267,28 +242,26 @@
         }
     }
 
-    private class FilterChildren extends Children.Keys implements ChangedListener<CheckNode> {
+    private class FilterChildren extends Children.Keys<Filter> implements ChangedListener<CheckNode> {
+
+        private HashMap<Filter, Node> nodeHash = new HashMap<>();
 
-        //private Node[] oldSelection;
-        //private ArrayList<Node> newSelection;
-        private HashMap<Object, Node> nodeHash = new HashMap<Object, Node>();
-
-        protected Node[] createNodes(Object object) {
-            if (nodeHash.containsKey(object)) {
-                return new Node[]{nodeHash.get(object)};
+        @Override
+        protected Node[] createNodes(Filter filter) {
+            if (nodeHash.containsKey(filter)) {
+                return new Node[]{nodeHash.get(filter)};
             }
 
-            assert object instanceof Filter;
-            Filter filter = (Filter) object;
-            com.sun.hotspot.igv.filterwindow.FilterNode node = new com.sun.hotspot.igv.filterwindow.FilterNode(filter);
+            FilterNode node = new FilterNode(filter);
             node.getSelectionChangedEvent().addListener(this);
-            nodeHash.put(object, node);
+            nodeHash.put(filter, node);
             return new Node[]{node};
         }
 
         public FilterChildren() {
             sequence.getChangedEvent().addListener(new ChangedListener<FilterChain>() {
 
+                @Override
                 public void changed(FilterChain source) {
                     addNotify();
                 }
@@ -297,11 +270,13 @@
             setBefore(false);
         }
 
+        @Override
         protected void addNotify() {
             setKeys(sequence.getFilters());
             updateSelection();
         }
 
+        @Override
         public void changed(CheckNode source) {
             FilterNode node = (FilterNode) source;
             Filter f = node.getFilter();
@@ -322,16 +297,11 @@
     }
 
     public FilterChain getFilterChain() {
-        return filterChain;/*
-    EditorTopComponent tc = EditorTopComponent.getActive();
-    if (tc == null) {
-    return filterChain;
-    }
-    return tc.getFilterChain();*/
+        return filterChain;
     }
 
     private FilterTopComponent() {
-        filterSettingsChangedEvent = new ChangedEvent<FilterTopComponent>(this);
+        filterSettingsChangedEvent = new ChangedEvent<>(this);
         initComponents();
         setName(NbBundle.getMessage(FilterTopComponent.class, "CTL_FilterTopComponent"));
         setToolTipText(NbBundle.getMessage(FilterTopComponent.class, "HINT_FilterTopComponent"));
@@ -355,13 +325,13 @@
         toolBar.add(SaveFilterSettingsAction.get(SaveFilterSettingsAction.class));
         toolBar.add(RemoveFilterSettingsAction.get(RemoveFilterSettingsAction.class));
         toolBar.addSeparator();
+        toolBar.add(NewFilterAction.get(NewFilterAction.class));
+        toolBar.add(RemoveFilterAction.get(RemoveFilterAction.class).createContextAwareInstance(this.getLookup()));
         toolBar.add(MoveFilterUpAction.get(MoveFilterUpAction.class).createContextAwareInstance(this.getLookup()));
         toolBar.add(MoveFilterDownAction.get(MoveFilterDownAction.class).createContextAwareInstance(this.getLookup()));
-        toolBar.add(RemoveFilterAction.get(RemoveFilterAction.class).createContextAwareInstance(this.getLookup()));
-        toolBar.add(NewFilterAction.get(NewFilterAction.class));
         this.add(view, BorderLayout.CENTER);
 
-        filterSettings = new ArrayList<FilterSetting>();
+        filterSettings = new ArrayList<>();
         updateComboBox();
 
         comboBox.addActionListener(comboBoxActionListener);
@@ -401,6 +371,7 @@
             filter = cf;
         }
 
+        @Override
         public void changed(Filter source) {
             try {
                 if (!fileObject.getName().equals(filter.getName())) {
@@ -409,15 +380,14 @@
                     lock.releaseLock();
                     FileObject newFileObject = fileObject.getParent().getFileObject(filter.getName());
                     fileObject = newFileObject;
-
                 }
 
                 FileLock lock = fileObject.lock();
                 OutputStream os = fileObject.getOutputStream(lock);
-                Writer w = new OutputStreamWriter(os);
-                String s = filter.getCode();
-                w.write(s);
-                w.close();
+                try (Writer w = new OutputStreamWriter(os)) {
+                    String s = filter.getCode();
+                    w.write(s);
+                }
                 lock.releaseLock();
 
             } catch (IOException ex) {
@@ -427,15 +397,13 @@
     }
 
     public void initFilters() {
-
-        FileSystem fs = Repository.getDefault().getDefaultFileSystem();
-        FileObject folder = fs.getRoot().getFileObject(FOLDER_ID);
+        FileObject folder = FileUtil.getConfigRoot().getFileObject(FOLDER_ID);
         FileObject[] children = folder.getChildren();
 
-        List<CustomFilter> customFilters = new ArrayList<CustomFilter>();
-        HashMap<CustomFilter, String> afterMap = new HashMap<CustomFilter, String>();
-        Set<CustomFilter> enabledSet = new HashSet<CustomFilter>();
-        HashMap<String, CustomFilter> map = new HashMap<String, CustomFilter>();
+        List<CustomFilter> customFilters = new ArrayList<>();
+        HashMap<CustomFilter, String> afterMap = new HashMap<>();
+        Set<CustomFilter> enabledSet = new HashSet<>();
+        HashMap<String, CustomFilter> map = new HashMap<>();
 
         for (final FileObject fo : children) {
             InputStream is = null;
@@ -447,13 +415,12 @@
                 is = fo.getInputStream();
                 BufferedReader r = new BufferedReader(new InputStreamReader(is));
                 String s;
-                StringBuffer sb = new StringBuffer();
+                StringBuilder sb = new StringBuilder();
                 while ((s = r.readLine()) != null) {
                     sb.append(s);
                     sb.append("\n");
                 }
                 code = sb.toString();
-
             } catch (FileNotFoundException ex) {
                 Exceptions.printStackTrace(ex);
             } catch (IOException ex) {
@@ -488,7 +455,7 @@
 
         for (int j = 0; j < customFilters.size(); j++) {
             for (int i = 0; i < customFilters.size(); i++) {
-                List<CustomFilter> copiedList = new ArrayList<CustomFilter>(customFilters);
+                List<CustomFilter> copiedList = new ArrayList<>(customFilters);
                 for (CustomFilter cf : copiedList) {
 
                     String after = afterMap.get(cf);
@@ -573,7 +540,7 @@
 
     @Override
     public void componentOpened() {
-        Lookup.Template<FilterChain> tpl = new Lookup.Template<FilterChain>(FilterChain.class);
+        Lookup.Template<FilterChain> tpl = new Lookup.Template<>(FilterChain.class);
         result = Utilities.actionsGlobalContext().lookup(tpl);
         result.addLookupListener(this);
     }
@@ -584,13 +551,9 @@
         result = null;
     }
 
+    @Override
     public void resultChanged(LookupEvent lookupEvent) {
         setChain(Utilities.actionsGlobalContext().lookup(FilterChain.class));
-    /*
-    EditorTopComponent tc = EditorTopComponent.getActive();
-    if (tc != null) {
-    setChain(tc.getFilterChain());
-    }*/
     }
 
     public void setChain(FilterChain chain) {
@@ -598,10 +561,10 @@
     }
 
     private FileObject getFileObject(CustomFilter cf) {
-        FileObject fo = Repository.getDefault().getDefaultFileSystem().getRoot().getFileObject(FOLDER_ID + "/" + cf.getName());
+        FileObject fo = FileUtil.getConfigRoot().getFileObject(FOLDER_ID + "/" + cf.getName());
         if (fo == null) {
             try {
-                fo = org.openide.filesystems.Repository.getDefault().getDefaultFileSystem().getRoot().getFileObject(FOLDER_ID).createData(cf.getName());
+                fo = FileUtil.getConfigRoot().getFileObject(FOLDER_ID).createData(cf.getName());
             } catch (IOException ex) {
                 Exceptions.printStackTrace(ex);
             }
@@ -610,6 +573,24 @@
     }
 
     @Override
+    public boolean requestFocus(boolean temporary) {
+        view.requestFocus();
+        return super.requestFocus(temporary);
+    }
+
+    @Override
+    protected boolean requestFocusInWindow(boolean temporary) {
+        view.requestFocus();
+        return super.requestFocusInWindow(temporary);
+    }
+
+    @Override
+    public void requestActive() {
+        super.requestActive();
+        view.requestFocus();
+    }
+
+    @Override
     public void writeExternal(ObjectOutput out) throws IOException {
         super.writeExternal(out);
 
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/actions/Bundle.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/actions/Bundle.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,10 +1,7 @@
-# To change this template, choose Tools | Templates
-# and open the template in the editor.
-
-CTL_FilterAction=Open Filter Window
+CTL_FilterAction=Filters
+CTL_MoveFilterUpAction=Move upwards
 CTL_MoveFilterDownAction=Move downwards
-CTL_MoveFilterUpAction=Move upwards
-CTL_NewFilterAction=New filter...
 CTL_RemoveFilterAction=Remove
 CTL_RemoveFilterSettingsAction=Remove filter setting
-CTL_SaveFilterSettingsAction=Save filter settings...
+CTL_SaveFilterSettingsAction=Create filter profile...
+CTL_NewFilterAction=New filter...
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/actions/FilterAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/actions/FilterAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,7 +23,7 @@
  */
 package com.sun.hotspot.igv.filterwindow.actions;
 
-import com.sun.hotspot.igv.filterwindow.*;
+import com.sun.hotspot.igv.filterwindow.FilterTopComponent;
 import java.awt.event.ActionEvent;
 import javax.swing.AbstractAction;
 import org.openide.util.NbBundle;
@@ -39,6 +39,7 @@
         super(NbBundle.getMessage(FilterAction.class, "CTL_FilterAction"));
     }
 
+    @Override
     public void actionPerformed(ActionEvent evt) {
         TopComponent win = FilterTopComponent.findInstance();
         win.open();
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/actions/MoveFilterDownAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/actions/MoveFilterDownAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,8 +23,8 @@
  */
 package com.sun.hotspot.igv.filterwindow.actions;
 
+import com.sun.hotspot.igv.filter.Filter;
 import com.sun.hotspot.igv.filterwindow.FilterTopComponent;
-import com.sun.hotspot.igv.filter.Filter;
 import javax.swing.Action;
 import org.openide.nodes.Node;
 import org.openide.util.HelpCtx;
@@ -37,6 +37,7 @@
  */
 public final class MoveFilterDownAction extends CookieAction {
 
+    @Override
     protected void performAction(Node[] activatedNodes) {
         for (Node n : activatedNodes) {
             Filter c = n.getLookup().lookup(Filter.class);
@@ -44,19 +45,22 @@
         }
     }
 
+    @Override
     protected int mode() {
         return CookieAction.MODE_EXACTLY_ONE;
     }
 
     public MoveFilterDownAction() {
 
-        putValue(Action.SHORT_DESCRIPTION, "Move filter downwards");
+        putValue(Action.SHORT_DESCRIPTION, "Move selected filter downwards");
     }
 
+    @Override
     public String getName() {
         return NbBundle.getMessage(MoveFilterUpAction.class, "CTL_MoveFilterDownAction");
     }
 
+    @Override
     protected Class[] cookieClasses() {
         return new Class[]{
             Filter.class
@@ -65,7 +69,7 @@
 
     @Override
     protected String iconResource() {
-        return "com/sun/hotspot/igv/filterwindow/images/down.gif";
+        return "com/sun/hotspot/igv/filterwindow/images/down.png";
     }
 
     @Override
@@ -74,6 +78,7 @@
         putValue("noIconInMenu", Boolean.TRUE);
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/actions/MoveFilterUpAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/actions/MoveFilterUpAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,8 +23,8 @@
  */
 package com.sun.hotspot.igv.filterwindow.actions;
 
+import com.sun.hotspot.igv.filter.Filter;
 import com.sun.hotspot.igv.filterwindow.FilterTopComponent;
-import com.sun.hotspot.igv.filter.Filter;
 import javax.swing.Action;
 import org.openide.nodes.Node;
 import org.openide.util.HelpCtx;
@@ -37,6 +37,7 @@
  */
 public final class MoveFilterUpAction extends CookieAction {
 
+    @Override
     protected void performAction(Node[] activatedNodes) {
         for (Node n : activatedNodes) {
             Filter c = n.getLookup().lookup(Filter.class);
@@ -44,18 +45,21 @@
         }
     }
 
+    @Override
     protected int mode() {
         return CookieAction.MODE_EXACTLY_ONE;
     }
 
     public MoveFilterUpAction() {
-        putValue(Action.SHORT_DESCRIPTION, "Move filter upwards");
+        putValue(Action.SHORT_DESCRIPTION, "Move selected filter upwards");
     }
 
+    @Override
     public String getName() {
         return NbBundle.getMessage(MoveFilterUpAction.class, "CTL_MoveFilterUpAction");
     }
 
+    @Override
     protected Class[] cookieClasses() {
         return new Class[]{
             Filter.class
@@ -64,7 +68,7 @@
 
     @Override
     protected String iconResource() {
-        return "com/sun/hotspot/igv/filterwindow/images/up.gif";
+        return "com/sun/hotspot/igv/filterwindow/images/up.png";
     }
 
     @Override
@@ -73,6 +77,7 @@
         putValue("noIconInMenu", Boolean.TRUE);
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/actions/NewFilterAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/actions/NewFilterAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -39,10 +39,12 @@
         putValue(Action.SHORT_DESCRIPTION, "Create new filter");
     }
 
+    @Override
     public void performAction() {
         FilterTopComponent.findInstance().newFilter();
     }
 
+    @Override
     public String getName() {
         return NbBundle.getMessage(SaveFilterSettingsAction.class, "CTL_NewFilterAction");
     }
@@ -52,6 +54,7 @@
         super.initialize();
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
@@ -63,6 +66,6 @@
 
     @Override
     protected String iconResource() {
-        return "com/sun/hotspot/igv/filterwindow/images/plus.gif";
+        return "com/sun/hotspot/igv/filterwindow/images/plus.png";
     }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/actions/RemoveFilterAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/actions/RemoveFilterAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,8 +23,8 @@
  */
 package com.sun.hotspot.igv.filterwindow.actions;
 
+import com.sun.hotspot.igv.filter.Filter;
 import com.sun.hotspot.igv.filterwindow.FilterTopComponent;
-import com.sun.hotspot.igv.filter.Filter;
 import javax.swing.Action;
 import javax.swing.JOptionPane;
 import org.openide.nodes.Node;
@@ -39,13 +39,14 @@
  */
 public final class RemoveFilterAction extends CookieAction {
 
+    @Override
     protected void performAction(Node[] activatedNodes) {
         Object[] options = {"Yes",
             "No",
             "Cancel"
         };
         int n = JOptionPane.showOptionDialog(WindowManager.getDefault().getMainWindow(),
-                "Do you really want to delete " + activatedNodes.length + " filter/s?", "Delete?",
+                "Do you really want to delete " + activatedNodes.length + " filter(s)?", "Delete Filters",
                 JOptionPane.YES_NO_CANCEL_OPTION,
                 JOptionPane.QUESTION_MESSAGE,
                 null,
@@ -59,18 +60,21 @@
         }
     }
 
+    @Override
     protected int mode() {
         return CookieAction.MODE_ALL;
     }
 
+    @Override
     public String getName() {
         return NbBundle.getMessage(RemoveFilterAction.class, "CTL_RemoveFilterAction");
     }
 
     public RemoveFilterAction() {
-        putValue(Action.SHORT_DESCRIPTION, "Remove filter");
+        putValue(Action.SHORT_DESCRIPTION, "Remove selected filter");
     }
 
+    @Override
     protected Class[] cookieClasses() {
         return new Class[]{
             Filter.class
@@ -85,9 +89,10 @@
 
     @Override
     protected String iconResource() {
-        return "com/sun/hotspot/igv/filterwindow/images/minus.gif";
+        return "com/sun/hotspot/igv/filterwindow/images/minus.png";
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/actions/RemoveFilterSettingsAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/actions/RemoveFilterSettingsAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -35,16 +35,18 @@
  */
 public final class RemoveFilterSettingsAction extends CallableSystemAction {
 
+    @Override
     public void performAction() {
         FilterTopComponent.findInstance().removeFilterSetting();
     }
 
+    @Override
     public String getName() {
         return NbBundle.getMessage(RemoveFilterSettingsAction.class, "CTL_RemoveFilterSettingsAction");
     }
 
     public RemoveFilterSettingsAction() {
-        putValue(Action.SHORT_DESCRIPTION, "Remove filter profile");
+        putValue(Action.SHORT_DESCRIPTION, "Delete current filter profile");
     }
 
     @Override
@@ -52,6 +54,7 @@
         super.initialize();
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
@@ -63,6 +66,6 @@
 
     @Override
     protected String iconResource() {
-        return "com/sun/hotspot/igv/filterwindow/images/delete.gif";
+        return "com/sun/hotspot/igv/filterwindow/images/delete.png";
     }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/actions/SaveFilterSettingsAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/actions/SaveFilterSettingsAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -35,10 +35,12 @@
  */
 public final class SaveFilterSettingsAction extends CallableSystemAction {
 
+    @Override
     public void performAction() {
         FilterTopComponent.findInstance().addFilterSetting();
     }
 
+    @Override
     public String getName() {
         return NbBundle.getMessage(SaveFilterSettingsAction.class, "CTL_SaveFilterSettingsAction");
     }
@@ -49,9 +51,10 @@
     }
 
     public SaveFilterSettingsAction() {
-        putValue(Action.SHORT_DESCRIPTION, "Create new filter profile");
+        putValue(Action.SHORT_DESCRIPTION, "Save filter configuration as profile...");
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
@@ -63,6 +66,6 @@
 
     @Override
     protected String iconResource() {
-        return "com/sun/hotspot/igv/filterwindow/images/add.gif";
+        return "com/sun/hotspot/igv/filterwindow/images/add.png";
     }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/customRightTopWsmode.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/customRightTopWsmode.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -4,8 +4,8 @@
     <kind type="view" />
     <state type="joined" />
     <constraints>
-        <path orientation="horizontal" number="45" weight="0.21761006289308177"/>
-        <path orientation="vertical" number="0" weight="0.2510122989593188"/>
+        <path orientation="horizontal" number="90" weight="0.2"/>
+        <path orientation="vertical" number="0" weight="0.75"/>
     </constraints>
     <bounds x="0" y="0" width="0" height="0" />
     <frame state="0"/>
Binary file hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/images/add.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/images/add.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/images/delete.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/images/delete.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/images/down.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/images/down.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/images/minus.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/images/minus.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/images/plus.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/images/plus.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/images/up.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/images/up.png has changed
--- a/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/layer.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/FilterWindow/src/com/sun/hotspot/igv/filterwindow/layer.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -18,8 +18,11 @@
             <attr name="position" intvalue="900"/>
         </file>
     </folder>
-    <folder name="Window">
-        <file name="com-sun-hotspot-igv-coordinator-actions-FilterAction.instance"/>
+    
+    <folder name="Actions">
+        <folder name="Window">
+            <file name="com-sun-hotspot-igv-filterwindow-actions-FilterAction.instance"/>
+        </folder>
     </folder>
     <folder name="Menu">
         <folder name="Window">
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graal/build.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,8 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- You may freely edit this file. See harness/README in the NetBeans platform -->
+<!-- for some information on what you could do (e.g. targets to override). -->
+<!-- If you delete this file and reopen the project it will be recreated. -->
+<project name="com.sun.hotspot.igv.graal" default="netbeans" basedir=".">
+    <description>Builds, tests, and runs the project com.sun.hotspot.igv.graal.</description>
+    <import file="nbproject/build-impl.xml"/>
+</project>
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graal/manifest.mf	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,6 @@
+Manifest-Version: 1.0
+OpenIDE-Module: com.sun.hotspot.igv.graal
+OpenIDE-Module-Layer: com/sun/hotspot/igv/graal/layer.xml
+OpenIDE-Module-Localizing-Bundle: com/sun/hotspot/igv/graal/Bundle.properties
+OpenIDE-Module-Specification-Version: 1.0
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graal/nbproject/build-impl.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,45 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+*** GENERATED FROM project.xml - DO NOT EDIT  ***
+***         EDIT ../build.xml INSTEAD         ***
+-->
+<project name="com.sun.hotspot.igv.graal-impl" basedir="..">
+    <fail message="Please build using Ant 1.7.1 or higher.">
+        <condition>
+            <not>
+                <antversion atleast="1.7.1"/>
+            </not>
+        </condition>
+    </fail>
+    <property file="nbproject/private/suite-private.properties"/>
+    <property file="nbproject/suite.properties"/>
+    <fail unless="suite.dir">You must set 'suite.dir' to point to your containing module suite</fail>
+    <property file="${suite.dir}/nbproject/private/platform-private.properties"/>
+    <property file="${suite.dir}/nbproject/platform.properties"/>
+    <macrodef name="property" uri="http://www.netbeans.org/ns/nb-module-project/2">
+        <attribute name="name"/>
+        <attribute name="value"/>
+        <sequential>
+            <property name="@{name}" value="${@{value}}"/>
+        </sequential>
+    </macrodef>
+    <macrodef name="evalprops" uri="http://www.netbeans.org/ns/nb-module-project/2">
+        <attribute name="property"/>
+        <attribute name="value"/>
+        <sequential>
+            <property name="@{property}" value="@{value}"/>
+        </sequential>
+    </macrodef>
+    <property file="${user.properties.file}"/>
+    <nbmproject2:property name="harness.dir" value="nbplatform.${nbplatform.active}.harness.dir" xmlns:nbmproject2="http://www.netbeans.org/ns/nb-module-project/2"/>
+    <nbmproject2:property name="nbplatform.active.dir" value="nbplatform.${nbplatform.active}.netbeans.dest.dir" xmlns:nbmproject2="http://www.netbeans.org/ns/nb-module-project/2"/>
+    <nbmproject2:evalprops property="cluster.path.evaluated" value="${cluster.path}" xmlns:nbmproject2="http://www.netbeans.org/ns/nb-module-project/2"/>
+    <fail message="Path to 'platform' cluster missing in $${cluster.path} property or using corrupt Netbeans Platform (missing harness).">
+        <condition>
+            <not>
+                <contains string="${cluster.path.evaluated}" substring="platform"/>
+            </not>
+        </condition>
+    </fail>
+    <import file="${harness.dir}/build.xml"/>
+</project>
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graal/nbproject/genfiles.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,8 @@
+build.xml.data.CRC32=92ea213f
+build.xml.script.CRC32=3534d355
+build.xml.stylesheet.CRC32=a56c6a5b@2.67.1
+# This file is used by a NetBeans-based IDE to track changes in generated files such as build-impl.xml.
+# Do not edit this file. You may delete it but then the IDE will never regenerate such files for you.
+nbproject/build-impl.xml.data.CRC32=92ea213f
+nbproject/build-impl.xml.script.CRC32=2867f2d5
+nbproject/build-impl.xml.stylesheet.CRC32=238281d1@2.67.1
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graal/nbproject/project.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,2 @@
+javac.source=1.7
+javac.compilerargs=-Xlint -Xlint:-serial
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graal/nbproject/project.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,45 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://www.netbeans.org/ns/project/1">
+    <type>org.netbeans.modules.apisupport.project</type>
+    <configuration>
+        <data xmlns="http://www.netbeans.org/ns/nb-module-project/3">
+            <code-name-base>com.sun.hotspot.igv.graal</code-name-base>
+            <suite-component/>
+            <module-dependencies>
+                <dependency>
+                    <code-name-base>com.sun.hotspot.igv.data</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>1.0</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>com.sun.hotspot.igv.filter</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>1.0</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>com.sun.hotspot.igv.layout</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>1.0</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>com.sun.hotspot.igv.graph</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>1.0</specification-version>
+                    </run-dependency>
+                </dependency>
+            </module-dependencies>
+            <public-packages/>
+        </data>
+    </configuration>
+</project>
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graal/nbproject/suite.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,1 @@
+suite.dir=${basedir}/..
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graal/src/com/sun/hotspot/igv/graal/Bundle.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,1 @@
+OpenIDE-Module-Name=Graal Compiler Support
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graal/src/com/sun/hotspot/igv/graal/filters/GraalCFGFilter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,89 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+package com.sun.hotspot.igv.graal.filters;
+
+import com.sun.hotspot.igv.data.Properties;
+import com.sun.hotspot.igv.filter.AbstractFilter;
+import com.sun.hotspot.igv.graph.Connection;
+import com.sun.hotspot.igv.graph.Diagram;
+import com.sun.hotspot.igv.graph.Figure;
+import com.sun.hotspot.igv.graph.InputSlot;
+import com.sun.hotspot.igv.graph.OutputSlot;
+import java.util.HashSet;
+import java.util.Set;
+
+public class GraalCFGFilter extends AbstractFilter {
+
+    @Override
+    public String getName() {
+        return "Graal CFG Filter";
+    }
+
+    @Override
+    public void apply(Diagram d) {
+        Set<Connection> connectionsToRemove = new HashSet<>();
+
+        for (Figure f : d.getFigures()) {
+            Properties p = f.getProperties();
+            int predCount;
+            String predCountString = p.get("predecessorCount");
+            if (predCountString != null) {
+                predCount = Integer.parseInt(predCountString);
+            } else if (Boolean.parseBoolean(p.get("hasPredecessor"))) {
+                predCount = 1;
+            } else {
+                predCount = 0;
+            }
+            for (InputSlot is : f.getInputSlots()) {
+                if (is.getPosition() >= predCount && !"EndNode".equals(is.getProperties().get("class"))) {
+                    for (Connection c : is.getConnections()) {
+                        if (!"EndNode".equals(c.getOutputSlot().getFigure().getProperties().get("class"))) {
+                            connectionsToRemove.add(c);
+                        }
+                    }
+                }
+            }
+        }
+
+        for (Connection c : connectionsToRemove) {
+            c.remove();
+        }
+
+        Set<Figure> figuresToRemove = new HashSet<>();
+        next: for (Figure f : d.getFigures()) {
+            for (InputSlot is : f.getInputSlots()) {
+                if (!is.getConnections().isEmpty()) {
+                    continue next;
+                }
+            }
+            for (OutputSlot os : f.getOutputSlots()) {
+                if (!os.getConnections().isEmpty()) {
+                    continue next;
+                }
+            }
+            figuresToRemove.add(f);
+        }
+        d.removeAllFigures(figuresToRemove);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graal/src/com/sun/hotspot/igv/graal/filters/GraalColoringFilter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,81 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+package com.sun.hotspot.igv.graal.filters;
+
+import com.sun.hotspot.igv.data.Properties;
+import com.sun.hotspot.igv.filter.AbstractFilter;
+import com.sun.hotspot.igv.graph.Diagram;
+import com.sun.hotspot.igv.graph.Figure;
+import java.awt.Color;
+import java.util.List;
+
+public class GraalColoringFilter extends AbstractFilter {
+
+    private String colorName;
+
+    public GraalColoringFilter(String colorName) {
+        this.colorName = colorName;
+    }
+
+    @Override
+    public String getName() {
+        return "Graal Coloring Filter (" + colorName + ")";
+    }
+
+    @Override
+    public void apply(Diagram d) {
+        List<Figure> figures = d.getFigures();
+        int colors = 0;
+        for (Figure f : figures) {
+            Properties p = f.getProperties();
+            final String prop = p.get(colorName + "Color");
+            if (prop == null) {
+                continue;
+            }
+            try {
+                int color = Integer.parseInt(prop);
+                if (color > colors) {
+                    colors = color;
+                }
+            } catch (NumberFormatException nfe) {
+                // nothing to do
+            }
+        }
+        colors++;
+        for (Figure f : figures) {
+            Properties p = f.getProperties();
+            final String prop = p.get(colorName + "Color");
+            if (prop == null) {
+                continue;
+            }
+            try {
+                int color = Integer.parseInt(prop);
+                Color c = Color.getHSBColor((float) color / colors, 1.0f, 0.7f);
+                f.setColor(c);
+            } catch (NumberFormatException nfe) {
+                // nothing to do
+            }
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graal/src/com/sun/hotspot/igv/graal/filters/GraalEdgeColorFilter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,97 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+package com.sun.hotspot.igv.graal.filters;
+
+import com.sun.hotspot.igv.data.Properties;
+import com.sun.hotspot.igv.filter.AbstractFilter;
+import com.sun.hotspot.igv.graph.Connection;
+import com.sun.hotspot.igv.graph.Connection.ConnectionStyle;
+import com.sun.hotspot.igv.graph.Diagram;
+import com.sun.hotspot.igv.graph.Figure;
+import com.sun.hotspot.igv.graph.InputSlot;
+import java.awt.Color;
+import java.util.HashMap;
+import java.util.List;
+
+/**
+ * Filter that colors usage and successor edges differently.
+ *
+ * @author Peter Hofer
+ */
+public class GraalEdgeColorFilter extends AbstractFilter {
+
+    private final HashMap<String,Color> usageColor = new HashMap<>();
+    private Color otherUsageColor = Color.BLACK;
+
+    public GraalEdgeColorFilter() {
+    }
+
+    @Override
+    public String getName() {
+        return "Graal Edge Color Filter";
+    }
+
+    @Override
+    public void apply(Diagram d) {
+        List<Figure> figures = d.getFigures();
+        for (Figure f : figures) {
+            for (InputSlot is : f.getInputSlots()) {
+                for (Connection c : is.getConnections()) {
+                    String type = c.getType();
+                    if (type == "Association" && "EndNode".equals(c.getOutputSlot().getFigure().getProperties().get("class"))) {
+                        type = "Successor";
+                    }
+
+                    if (type != null) {
+                        Color typeColor = usageColor.get(type);
+                        if (typeColor == null) {
+                            c.setColor(otherUsageColor);
+                        } else {
+                            c.setColor(typeColor);
+                        }
+                        if (c.getStyle() != ConnectionStyle.DASHED && type == "Successor") {
+                            c.setStyle(ConnectionStyle.BOLD);
+                        }
+                    }
+                }
+            }
+        }
+    }
+
+    public Color getUsageColor(String type) {
+        return usageColor.get(type);
+    }
+
+    public void setUsageColor(String type, Color usageColor) {
+        this.usageColor.put(type, usageColor);
+    }
+
+    public Color getOtherUsageColor() {
+        return otherUsageColor;
+    }
+
+    public void setOtherUsageColor(Color otherUsageColor) {
+        this.otherUsageColor = otherUsageColor;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graal/src/com/sun/hotspot/igv/graal/filters/callgraph.filter	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,4 @@
+colorize("name", "<init>.*", yellow);
+colorize("name", "<clinit>.*", pink);
+colorize("leaf", "1", lightGray);
+colorize("cutoff", "1", red);
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graal/src/com/sun/hotspot/igv/graal/filters/color.filter	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,31 @@
+var red =  new java.awt.Color(240, 59, 32);
+var orange = new java.awt.Color(254, 178, 76);
+var yellow = new java.awt.Color(255, 237, 160);
+var middleBlue = new java.awt.Color(100, 147, 224);
+var lightGreen = new java.awt.Color(173, 221, 142);
+var lightBlue = new java.awt.Color(200, 200, 250);
+var gray = new java.awt.Color(220, 220, 220);
+var violet = new java.awt.Color(201, 148, 199);
+var black = new java.awt.Color(0, 0, 0);
+
+colorize("category", "controlSink", red);
+colorize("category", "controlSplit", red);
+colorize("category", "merge", red);
+colorize("category", "begin", orange);
+colorize("category", "end", orange);
+colorize("category", "fixed", yellow);
+colorize("category", "state", lightGreen);
+colorize("category", "phi", middleBlue);
+colorize("category", "proxy", middleBlue);
+colorize("category", "floating", lightBlue);
+colorize("class", "ConstantLocationNode", gray);
+colorize("class", "ParameterNode", gray);
+colorize("class", "ConstantNode", gray);
+colorize("class", "GuardNode", violet);
+colorize("class", "BlackholeNode", black);
+
+var f = new com.sun.hotspot.igv.graal.filters.GraalEdgeColorFilter();
+f.setUsageColor("Successor", red);
+f.setUsageColor("Value", blue);
+f.setUsageColor("Memory", new Color(0.0, 0.5, 0.0));
+f.apply(graph);
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graal/src/com/sun/hotspot/igv/graal/filters/probability.filter	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,3 @@
+colorizeGradientWithMode("probability", 0, 500, "logarithmic");
+
+// more parameters: colorizeGradientCustom("probability", 0, 500, "logarithmic", [blue, yellow, red], [0, 0.5, 1], 16);
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graal/src/com/sun/hotspot/igv/graal/filters/reduceEdges.filter	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,3 @@
+split("class", "ConstantLocationNode");
+split("class", "ParameterNode");
+split("class", "ConstantNode");
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graal/src/com/sun/hotspot/igv/graal/filters/removeFloating.filter	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,4 @@
+remove("category", "floating");
+remove("category", "state");
+remove("category", "phi");
+remove("category", "proxy");
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graal/src/com/sun/hotspot/igv/graal/filters/removeState.filter	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,1 @@
+remove("category", "state");
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graal/src/com/sun/hotspot/igv/graal/filters/stampColor.filter	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,16 @@
+var red =  new java.awt.Color(240, 59, 32);
+var orange = new java.awt.Color(254, 178, 76);
+var yellow = new java.awt.Color(255, 237, 160);
+var middleBlue = new java.awt.Color(100, 147, 224);
+var lightGreen = new java.awt.Color(173, 221, 142);
+var lightBlue = new java.awt.Color(200, 200, 250);
+var gray = new java.awt.Color(220, 220, 220);
+var violet = new java.awt.Color(201, 148, 199);
+
+colorize("stamp", ".*", white);
+colorize("stamp", "void", gray);
+colorize("stamp", "a.*", yellow);
+colorize("stamp", "a#.*", orange);
+colorize("stamp", "a!.*", red);
+colorize("stamp", "i.*", middleBlue);
+colorize("stamp", "f.*", lightGreen);
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graal/src/com/sun/hotspot/igv/graal/layer.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE filesystem PUBLIC "-//NetBeans//DTD Filesystem 1.1//EN" "http://www.netbeans.org/dtds/filesystem-1_1.dtd">
+<filesystem>
+    <folder name="Filters">
+        <file name="Coloring" url="filters/color.filter">
+            <attr name="enabled" boolvalue="true"/>
+        </file>
+        
+        
+        <file name="Stamp Coloring" url="filters/stampColor.filter">
+            <attr name="enabled" boolvalue="false"/>
+        </file>
+      
+        <file name="Probability Coloring" url="filters/probability.filter">
+            <attr name="enabled" boolvalue="false"/>
+        </file>
+        
+        <file name="Call Graph Coloring" url="filters/callgraph.filter">
+            <attr name="enabled" boolvalue="false"/>
+        </file>
+        
+        <file name="Reduce Edges" url="filters/reduceEdges.filter">
+            <attr name="enabled" boolvalue="true"/>
+        </file>
+        
+        <file name="Remove State" url="filters/removeState.filter">
+            <attr name="enabled" boolvalue="false"/>
+        </file>
+        
+        <file name="Remove Floating" url="filters/removeFloating.filter">
+            <attr name="enabled" boolvalue="false"/>
+        </file>
+    </folder>
+</filesystem>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Graph/nbproject/project.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graph/nbproject/project.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,2 +1,2 @@
-javac.source=1.5
-javac.compilerargs=-Xlint -Xlint:-serial
+javac.source=1.7
+javac.compilerargs=-Xlint -Xlint:-serial
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Graph/nbproject/project.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graph/nbproject/project.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -25,6 +25,7 @@
             </module-dependencies>
             <public-packages>
                 <package>com.sun.hotspot.igv.graph</package>
+                <package>com.sun.hotspot.igv.graph.services</package>
             </public-packages>
         </data>
     </configuration>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/AndSelector.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/AndSelector.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -40,10 +40,11 @@
         this.selector2 = s2;
     }
 
+    @Override
     public List<Figure> selected(Diagram d) {
         List<Figure> l1 = selector1.selected(d);
         List<Figure> l2 = selector2.selected(d);
-        List<Figure> result = new ArrayList<Figure>();
+        List<Figure> result = new ArrayList<>();
         for (Figure f : l2) {
             if (l1.contains(f)) {
                 result.add(f);
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/Block.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/Block.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -60,14 +60,6 @@
         return succs;
     }
 
-    public Set<? extends Cluster> getPredecessors() {
-        Set<Block> succs = new HashSet<Block>();
-        for (InputBlock b : inputBlock.getPredecessors()) {
-            succs.add(diagram.getBlock(b));
-        }
-        return succs;
-    }
-
     public void setBounds(Rectangle r) {
         this.bounds = r;
     }
@@ -79,4 +71,10 @@
     public int compareTo(Cluster o) {
         return toString().compareTo(o.toString());
     }
+
+    @Override
+    public String toString() {
+        return inputBlock.getName();
+    }
 }
+
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/Connection.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/Connection.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,6 +23,7 @@
  */
 package com.sun.hotspot.igv.graph;
 
+import com.sun.hotspot.igv.data.Source;
 import com.sun.hotspot.igv.layout.Link;
 import com.sun.hotspot.igv.layout.Port;
 import java.awt.Color;
@@ -36,6 +37,11 @@
  */
 public class Connection implements Source.Provider, Link {
 
+    @Override
+    public boolean isVIP() {
+        return style == ConnectionStyle.BOLD;
+    }
+
     public enum ConnectionStyle {
 
         NORMAL,
@@ -48,13 +54,17 @@
     private Color color;
     private ConnectionStyle style;
     private List<Point> controlPoints;
+    private String label;
+    private String type;
 
-    protected Connection(InputSlot inputSlot, OutputSlot outputSlot) {
+    protected Connection(InputSlot inputSlot, OutputSlot outputSlot, String label, String type) {
         this.inputSlot = inputSlot;
         this.outputSlot = outputSlot;
+        this.label = label;
+        this.type = type;
         this.inputSlot.connections.add(this);
         this.outputSlot.connections.add(this);
-        controlPoints = new ArrayList<Point>();
+        controlPoints = new ArrayList<>();
         Figure sourceFigure = this.outputSlot.getFigure();
         Figure destFigure = this.inputSlot.getFigure();
         sourceFigure.addSuccessor(destFigure);
@@ -89,10 +99,19 @@
         style = s;
     }
 
+    @Override
     public Source getSource() {
         return source;
     }
 
+    public String getLabel() {
+        return label;
+    }
+
+    public String getType() {
+        return type;
+    }
+
     public void remove() {
         inputSlot.getFigure().removePredecessor(outputSlot.getFigure());
         inputSlot.connections.remove(this);
@@ -100,24 +119,44 @@
         outputSlot.connections.remove(this);
     }
 
+    public String getToolTipText() {
+        StringBuilder builder = new StringBuilder();
+        if (label != null) {
+            builder.append(label).append(": ");
+        }
+        if (type != null) {
+            builder.append(type).append(" ");
+        }
+        builder.append("from ");
+        builder.append(getOutputSlot().getFigure().getSource().getSourceNodes().get(0).getId());
+        builder.append(" to ");
+        builder.append(getInputSlot().getFigure().getSource().getSourceNodes().get(0).getId());
+        return builder.toString();
+    }
+
     @Override
     public String toString() {
-        return "Connection(" + getFrom().getVertex() + " to " + getTo().getVertex() + ")";
+        return "Connection('" + label + "', " + getFrom().getVertex() + " to " + getTo().getVertex() + ")";
     }
 
+    @Override
     public Port getFrom() {
         return outputSlot;
     }
 
+    @Override
     public Port getTo() {
         return inputSlot;
     }
 
+    @Override
     public List<Point> getControlPoints() {
         return controlPoints;
     }
 
+    @Override
     public void setControlPoints(List<Point> list) {
         controlPoints = list;
     }
 }
+
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/Diagram.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/Diagram.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -28,17 +28,9 @@
 import com.sun.hotspot.igv.data.InputGraph;
 import com.sun.hotspot.igv.data.InputNode;
 import com.sun.hotspot.igv.data.Properties;
+import com.sun.hotspot.igv.data.Properties.StringPropertyMatcher;
 import java.awt.Font;
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.Collections;
-import java.util.Comparator;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
+import java.util.*;
 
 /**
  *
@@ -51,20 +43,33 @@
     private InputGraph graph;
     private int curId;
     private String nodeText;
-    private Font font;
+    private final Font font;
+    private final Font slotFont;
+    private final Font boldFont;
 
     public Font getFont() {
         return font;
     }
 
+    public Font getSlotFont() {
+        return slotFont;
+    }
+
+    public Font getBoldFont() {
+        return boldFont;
+    }
+
     private Diagram() {
-        figures = new ArrayList<Figure>();
-        blocks = new HashMap<InputBlock, Block>();
+        figures = new ArrayList<>();
+        blocks = new LinkedHashMap<>(8);
         this.nodeText = "";
-        this.font = new Font("Serif", Font.PLAIN, 14);
+        this.font = new Font("Arial", Font.PLAIN, 12);
+        this.slotFont = new Font("Arial", Font.PLAIN, 10);
+        this.boldFont = this.font.deriveFont(Font.BOLD);
     }
 
     public Block getBlock(InputBlock b) {
+        assert blocks.containsKey(b);
         return blocks.get(b);
     }
 
@@ -72,12 +77,7 @@
         return nodeText;
     }
 
-    public void schedule(Collection<InputBlock> newBlocks) {
-        graph.schedule(newBlocks);
-        updateBlocks();
-    }
-
-    private void updateBlocks() {
+    public void updateBlocks() {
         blocks.clear();
         for (InputBlock b : graph.getBlocks()) {
             Block curBlock = new Block(b, this);
@@ -108,10 +108,26 @@
         return f;
     }
 
-    public Connection createConnection(InputSlot inputSlot, OutputSlot outputSlot) {
+    public Connection createConnection(InputSlot inputSlot, OutputSlot outputSlot, String label, String type) {
         assert inputSlot.getFigure().getDiagram() == this;
         assert outputSlot.getFigure().getDiagram() == this;
-        return new Connection(inputSlot, outputSlot);
+        return new Connection(inputSlot, outputSlot, label, type);
+    }
+
+    public Map<InputNode, Set<Figure>> calcSourceToFigureRelation() {
+        Map<InputNode, Set<Figure>> map = new HashMap<>();
+
+        for(InputNode node : this.getGraph().getNodes()) {
+            map.put(node, new HashSet<Figure>());
+        }
+
+        for(Figure f : this.getFigures()) {
+            for(InputNode node : f.getSource().getSourceNodes()) {
+                map.get(node).add(f);
+            }
+        }
+
+        return map;
     }
 
     public static Diagram createDiagram(InputGraph graph, String nodeText) {
@@ -126,11 +142,12 @@
         d.updateBlocks();
 
         Collection<InputNode> nodes = graph.getNodes();
-        HashMap<Integer, Figure> figureHash = new HashMap<Integer, Figure>();
+        Hashtable<Integer, Figure> figureHash = new Hashtable<>();
         for (InputNode n : nodes) {
             Figure f = d.createFigure();
             f.getSource().addSourceNode(n);
             f.getProperties().add(n.getProperties());
+            f.setSubgraphs(n.getSubgraphs());
             figureHash.put(n.getId(), f);
         }
 
@@ -140,23 +157,23 @@
             int to = e.getTo();
             Figure fromFigure = figureHash.get(from);
             Figure toFigure = figureHash.get(to);
+
+            if(fromFigure == null || toFigure == null) continue;
             assert fromFigure != null && toFigure != null;
 
+            int fromIndex = e.getFromIndex();
+            while (fromFigure.getOutputSlots().size() <= fromIndex) {
+                fromFigure.createOutputSlot();
+            }
+            OutputSlot outputSlot = fromFigure.getOutputSlots().get(fromIndex);
+
             int toIndex = e.getToIndex();
-
-            while (fromFigure.getOutputSlots().size() <= 0) {
-                fromFigure.createOutputSlot();
-            }
-
-            OutputSlot outputSlot = fromFigure.getOutputSlots().get(0);
-
             while (toFigure.getInputSlots().size() <= toIndex) {
                 toFigure.createInputSlot();
             }
-
             InputSlot inputSlot = toFigure.getInputSlots().get(toIndex);
 
-            Connection c = d.createConnection(inputSlot, outputSlot);
+            Connection c = d.createConnection(inputSlot, outputSlot, e.getLabel(), e.getType());
 
             if (e.getState() == InputEdge.State.NEW) {
                 c.setStyle(Connection.ConnectionStyle.BOLD);
@@ -174,7 +191,7 @@
             freeFigure(f);
         }
 
-        ArrayList<Figure> newFigures = new ArrayList<Figure>();
+        ArrayList<Figure> newFigures = new ArrayList<>();
         for (Figure f : this.figures) {
             if (!figuresToRemove.contains(f)) {
                 newFigures.add(f);
@@ -185,12 +202,12 @@
 
     private void freeFigure(Figure succ) {
 
-        List<InputSlot> inputSlots = new ArrayList<InputSlot>(succ.getInputSlots());
+        List<InputSlot> inputSlots = new ArrayList<>(succ.getInputSlots());
         for (InputSlot s : inputSlots) {
             succ.removeInputSlot(s);
         }
 
-        List<OutputSlot> outputSlots = new ArrayList<OutputSlot>(succ.getOutputSlots());
+        List<OutputSlot> outputSlots = new ArrayList<>(succ.getOutputSlots());
         for (OutputSlot s : outputSlots) {
             succ.removeOutputSlot(s);
         }
@@ -219,7 +236,7 @@
 
     public Set<Connection> getConnections() {
 
-        Set<Connection> connections = new HashSet<Connection>();
+        Set<Connection> connections = new HashSet<>();
         for (Figure f : figures) {
 
             for (InputSlot s : f.getInputSlots()) {
@@ -231,10 +248,10 @@
     }
 
     public Figure getRootFigure() {
-        Properties.PropertySelector<Figure> selector = new Properties.PropertySelector<Figure>(figures);
-        Figure root = selector.selectSingle("name", "Root");
+        Properties.PropertySelector<Figure> selector = new Properties.PropertySelector<>(figures);
+        Figure root = selector.selectSingle(new StringPropertyMatcher("name", "Root"));
         if (root == null) {
-            root = selector.selectSingle("name", "Start");
+            root = selector.selectSingle(new StringPropertyMatcher("name", "Start"));
         }
         if (root == null) {
             List<Figure> rootFigures = getRootFigures();
@@ -258,9 +275,10 @@
         System.out.println("Number of figures: " + tmpFigures.size());
         System.out.println("Number of connections: " + connections.size());
 
-        List<Figure> figuresSorted = new ArrayList<Figure>(tmpFigures);
+        List<Figure> figuresSorted = new ArrayList<>(tmpFigures);
         Collections.sort(figuresSorted, new Comparator<Figure>() {
 
+            @Override
             public int compare(Figure a, Figure b) {
                 return b.getPredecessors().size() + b.getSuccessors().size() - a.getPredecessors().size() - a.getSuccessors().size();
             }
@@ -283,7 +301,7 @@
     }
 
     public List<Figure> getRootFigures() {
-        ArrayList<Figure> rootFigures = new ArrayList<Figure>();
+        ArrayList<Figure> rootFigures = new ArrayList<>();
         for (Figure f : figures) {
             if (f.getPredecessors().size() == 0) {
                 rootFigures.add(f);
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/Figure.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/Figure.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,30 +23,25 @@
  */
 package com.sun.hotspot.igv.graph;
 
+import com.sun.hotspot.igv.data.InputBlock;
+import com.sun.hotspot.igv.data.InputGraph;
+import com.sun.hotspot.igv.data.InputNode;
+import com.sun.hotspot.igv.data.Properties;
+import com.sun.hotspot.igv.data.Source;
 import com.sun.hotspot.igv.layout.Cluster;
 import com.sun.hotspot.igv.layout.Vertex;
-import com.sun.hotspot.igv.data.Properties;
-import java.awt.Color;
-import java.awt.Dimension;
-import java.awt.FontMetrics;
-import java.awt.Graphics;
-import java.awt.Point;
+import java.awt.*;
 import java.awt.image.BufferedImage;
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.HashSet;
 import java.util.List;
-import java.util.Set;
+import java.util.*;
 
-/**
- *
- * @author Thomas Wuerthinger
- */
 public class Figure extends Properties.Entity implements Source.Provider, Vertex {
 
-    public static final int INSET = 6;
-    public static final int SLOT_WIDTH = 10;
-    public static final int SLOT_START = 3;
+    public static final int INSET = 8;
+    public static int SLOT_WIDTH = 10;
+    public static final int OVERLAPPING = 6;
+    public static final int SLOT_START = 4;
+    public static final int SLOT_OFFSET = 8;
     public static final boolean VERTICAL_LAYOUT = true;
     protected List<InputSlot> inputSlots;
     protected List<OutputSlot> outputSlots;
@@ -55,6 +50,7 @@
     private Point position;
     private List<Figure> predecessors;
     private List<Figure> successors;
+    private List<InputGraph> subgraphs;
     private Color color;
     private int id;
     private String idString;
@@ -66,7 +62,7 @@
         if (heightCash == -1) {
             BufferedImage image = new BufferedImage(1, 1, BufferedImage.TYPE_INT_RGB);
             Graphics g = image.getGraphics();
-            g.setFont(diagram.getFont());
+            g.setFont(diagram.getFont().deriveFont(Font.BOLD));
             FontMetrics metrics = g.getFontMetrics();
             String nodeText = diagram.getNodeText();
             heightCash = nodeText.split("\n").length * metrics.getHeight() + INSET;
@@ -74,20 +70,41 @@
         return heightCash;
     }
 
+    public static <T> List<T> getAllBefore(List<T> inputList, T tIn) {
+        List<T> result = new ArrayList<>();
+        for(T t : inputList) {
+            if(t.equals(tIn)) {
+                break;
+            }
+            result.add(t);
+        }
+        return result;
+    }
+
+    public static int getSlotsWidth(Collection<? extends Slot> slots) {
+        int result = Figure.SLOT_OFFSET;
+        for(Slot s : slots) {
+            result += s.getWidth() + Figure.SLOT_OFFSET;
+        }
+        return result;
+    }
+
     public int getWidth() {
         if (widthCash == -1) {
             int max = 0;
             BufferedImage image = new BufferedImage(1, 1, BufferedImage.TYPE_INT_RGB);
             Graphics g = image.getGraphics();
-            g.setFont(diagram.getFont());
+            g.setFont(diagram.getFont().deriveFont(Font.BOLD));
             FontMetrics metrics = g.getFontMetrics();
-            for (String s : lines) {
+            for (String s : getLines()) {
                 int cur = metrics.stringWidth(s);
                 if (cur > max) {
                     max = cur;
                 }
             }
             widthCash = max + INSET;
+            widthCash = Math.max(widthCash, Figure.getSlotsWidth(inputSlots));
+            widthCash = Math.max(widthCash, Figure.getSlotsWidth(outputSlots));
         }
         return widthCash;
     }
@@ -95,10 +112,10 @@
     protected Figure(Diagram diagram, int id) {
         this.diagram = diagram;
         this.source = new Source();
-        inputSlots = new ArrayList<InputSlot>(5);
-        outputSlots = new ArrayList<OutputSlot>(1);
-        predecessors = new ArrayList<Figure>(6);
-        successors = new ArrayList<Figure>(6);
+        inputSlots = new ArrayList<>(5);
+        outputSlots = new ArrayList<>(1);
+        predecessors = new ArrayList<>(6);
+        successors = new ArrayList<>(6);
         this.id = id;
         idString = Integer.toString(id);
 
@@ -123,7 +140,7 @@
     }
 
     public Set<Figure> getPredecessorSet() {
-        Set<Figure> result = new HashSet<Figure>();
+        Set<Figure> result = new HashSet<>();
         for (Figure f : getPredecessors()) {
             result.add(f);
         }
@@ -131,7 +148,7 @@
     }
 
     public Set<Figure> getSuccessorSet() {
-        Set<Figure> result = new HashSet<Figure>();
+        Set<Figure> result = new HashSet<>();
         for (Figure f : getSuccessors()) {
             result.add(f);
         }
@@ -160,10 +177,20 @@
         successors.remove(f);
     }
 
+    public List<InputGraph> getSubgraphs() {
+        return subgraphs;
+    }
+
+    public void setSubgraphs(List<InputGraph> subgraphs) {
+        this.subgraphs = subgraphs;
+    }
+
+    @Override
     public void setPosition(Point p) {
         this.position = p;
     }
 
+    @Override
     public Point getPosition() {
         return position;
     }
@@ -172,6 +199,7 @@
         return diagram;
     }
 
+    @Override
     public Source getSource() {
         return source;
     }
@@ -193,7 +221,7 @@
 
         assert inputSlots.contains(s) || outputSlots.contains(s);
 
-        List<Connection> connections = new ArrayList<Connection>(s.getConnections());
+        List<Connection> connections = new ArrayList<>(s.getConnections());
         for (Connection c : connections) {
             c.remove();
         }
@@ -222,6 +250,13 @@
         return Collections.unmodifiableList(inputSlots);
     }
 
+    public Set<Slot> getSlots() {
+        Set<Slot> result = new HashSet<>();
+        result.addAll(getInputSlots());
+        result.addAll(getOutputSlots());
+        return result;
+    }
+
     public List<OutputSlot> getOutputSlots() {
         return Collections.unmodifiableList(outputSlots);
     }
@@ -248,13 +283,13 @@
         String[] result = new String[strings.length];
 
         for (int i = 0; i < strings.length; i++) {
-            result[i] = resolveString(strings[i]);
+            result[i] = resolveString(strings[i], getProperties());
         }
 
         lines = result;
     }
 
-    private String resolveString(String string) {
+    public static final String resolveString(String string, Properties properties) {
 
         StringBuilder sb = new StringBuilder();
         boolean inBrackets = false;
@@ -264,7 +299,7 @@
             char c = string.charAt(i);
             if (inBrackets) {
                 if (c == ']') {
-                    String value = getProperties().get(curIdent.toString());
+                    String value = properties.get(curIdent.toString());
                     if (value == null) {
                         value = "";
                     }
@@ -286,13 +321,16 @@
         return sb.toString();
     }
 
+    @Override
     public Dimension getSize() {
         if (VERTICAL_LAYOUT) {
             int width = Math.max(getWidth(), Figure.SLOT_WIDTH * (Math.max(inputSlots.size(), outputSlots.size()) + 1));
-            int height = getHeight() + 2 * Figure.SLOT_WIDTH;
+            int height = getHeight() + 2 * Figure.SLOT_WIDTH - 2 * Figure.OVERLAPPING;
+
+
             return new Dimension(width, height);
         } else {
-            int width = getWidth() + 2 * Figure.SLOT_WIDTH;
+            int width = getWidth() + 2 * Figure.SLOT_WIDTH - 2*Figure.OVERLAPPING;
             int height = Figure.SLOT_WIDTH * (Math.max(inputSlots.size(), outputSlots.size()) + 1);
             return new Dimension(width, height);
         }
@@ -308,21 +346,31 @@
             assert false : "Should never reach here, every figure must have at least one source node!";
             return null;
         } else {
-            Cluster result = diagram.getBlock(diagram.getGraph().getBlock(getSource().getSourceNodes().get(0)));
+            final InputBlock inputBlock = diagram.getGraph().getBlock(getSource().getSourceNodes().get(0));
+            assert inputBlock != null;
+            Cluster result = diagram.getBlock(inputBlock);
             assert result != null;
             return result;
         }
     }
 
+    @Override
     public boolean isRoot() {
-        if (source.getSourceNodes().size() > 0 && source.getSourceNodes().get(0).getProperties().get("name").equals("Root")) {
-            return true;
+
+        List<InputNode> sourceNodes = source.getSourceNodes();
+        if (sourceNodes.size() > 0 && sourceNodes.get(0).getProperties().get("name") != null) {
+            return source.getSourceNodes().get(0).getProperties().get("name").equals("Root");
         } else {
             return false;
         }
     }
 
+    @Override
     public int compareTo(Vertex f) {
         return toString().compareTo(f.toString());
     }
+
+    public Rectangle getBounds() {
+        return new Rectangle(this.getPosition(), new Dimension(this.getWidth(), this.getHeight()));
+    }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/InputSlot.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/InputSlot.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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,18 +36,24 @@
         super(figure, wantedIndex);
     }
 
+    @Override
     public int getPosition() {
         return getFigure().getInputSlots().indexOf(this);
     }
 
+    @Override
     public void setPosition(int position) {
         List<InputSlot> inputSlots = getFigure().inputSlots;
         InputSlot s = inputSlots.remove(position);
         inputSlots.add(position, s);
     }
-
+    @Override
     public Point getRelativePosition() {
-        return new Point(getFigure().getWidth() * (getPosition() + 1) / (getFigure().getInputSlots().size() + 1), Figure.SLOT_WIDTH - Figure.SLOT_START);
+        int gap = getFigure().getWidth() - Figure.getSlotsWidth(getFigure().getInputSlots());
+        double gapRatio = (double)gap / (double)(getFigure().getInputSlots().size() + 1);
+        int gapAmount = (int)((getPosition() + 1)*gapRatio);
+        return new Point(gapAmount + Figure.getSlotsWidth(Figure.getAllBefore(getFigure().getInputSlots(), this)) + getWidth()/2, -Figure.SLOT_START);
+        //return new Point((getFigure().getWidth() / (getFigure().getInputSlots().size() * 2)) * (getPosition() * 2 + 1), -Figure.SLOT_START);
     }
 
     @Override
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/InvertSelector.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/InvertSelector.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -38,9 +38,10 @@
         this.selector = selector;
     }
 
+    @Override
     public List<Figure> selected(Diagram d) {
 
-        List<Figure> result = new ArrayList<Figure>();
+        List<Figure> result = new ArrayList<>();
         List<Figure> otherResult = selector.selected(d);
         for (Figure f : d.getFigures()) {
             if (!otherResult.contains(f)) {
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/MatcherSelector.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/MatcherSelector.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -39,8 +39,9 @@
         this.matcher = matcher;
     }
 
+    @Override
     public List<Figure> selected(Diagram d) {
-        Properties.PropertySelector<Figure> selector = new Properties.PropertySelector<Figure>(d.getFigures());
+        Properties.PropertySelector<Figure> selector = new Properties.PropertySelector<>(d.getFigures());
         List<Figure> list = selector.selectMultiple(matcher);
         return list;
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/OrSelector.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/OrSelector.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -40,6 +40,7 @@
         this.selector2 = s2;
     }
 
+    @Override
     public List<Figure> selected(Diagram d) {
 
         List<Figure> l1 = selector1.selected(d);
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/OutputSlot.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/OutputSlot.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -35,17 +35,26 @@
         super(figure, wantedIndex);
     }
 
+    @Override
     public int getPosition() {
         return getFigure().getOutputSlots().indexOf(this);
     }
 
+    @Override
     public void setPosition(int position) {
         OutputSlot s = getFigure().outputSlots.remove(position);
         getFigure().outputSlots.add(position, s);
     }
 
+    @Override
     public Point getRelativePosition() {
-        return new Point(getFigure().getWidth() * (getPosition() + 1) / (getFigure().getOutputSlots().size() + 1), getFigure().getSize().height - Figure.SLOT_WIDTH + Figure.SLOT_START);
+        int gap = getFigure().getWidth() - Figure.getSlotsWidth(getFigure().getOutputSlots());
+        if(gap < 0) {
+            gap = 0;
+        }
+        double gapRatio = (double)gap / (double)(getFigure().getOutputSlots().size() + 1);
+        int gapAmount = (int)((getPosition() + 1)*gapRatio);
+        return new Point(gapAmount + Figure.getSlotsWidth(Figure.getAllBefore(getFigure().getOutputSlots(), this)) + getWidth()/2, Figure.SLOT_START);
     }
 
     @Override
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/PredecessorSelector.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/PredecessorSelector.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -38,9 +38,10 @@
         this.innerSelector = innerSelector;
     }
 
+    @Override
     public List<Figure> selected(Diagram d) {
         List<Figure> inner = innerSelector.selected(d);
-        List<Figure> result = new ArrayList<Figure>();
+        List<Figure> result = new ArrayList<>();
         for (Figure f : d.getFigures()) {
             boolean saved = false;
             for (Figure f2 : f.getSuccessors()) {
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/Selector.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/Selector.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/Slot.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/Slot.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,63 +23,111 @@
  */
 package com.sun.hotspot.igv.graph;
 
+import com.sun.hotspot.igv.data.InputNode;
+import com.sun.hotspot.igv.data.Properties;
+import com.sun.hotspot.igv.data.Source;
 import com.sun.hotspot.igv.layout.Port;
 import com.sun.hotspot.igv.layout.Vertex;
+import java.awt.Color;
+import java.awt.Font;
+import java.awt.FontMetrics;
+import java.awt.Graphics;
+import java.awt.image.BufferedImage;
 import java.util.ArrayList;
 import java.util.Collections;
+import java.util.Comparator;
 import java.util.List;
-import java.util.Comparator;
 
 /**
  *
  * @author Thomas Wuerthinger
  */
-public abstract class Slot implements Port, Source.Provider {
+public abstract class Slot implements Port, Source.Provider, Properties.Provider {
 
     private int wantedIndex;
-    private String name;
-    private String shortName; // 1 - 2 characters
     private Source source;
     protected List<Connection> connections;
+    private InputNode associatedNode;
+    private Color color;
+    private String text;
+    private String shortName;
     private Figure figure;
 
     protected Slot(Figure figure, int wantedIndex) {
         this.figure = figure;
-        connections = new ArrayList<Connection>(2);
+        connections = new ArrayList<>(2);
         source = new Source();
         this.wantedIndex = wantedIndex;
-        name = "";
+        text = "";
         shortName = "";
         assert figure != null;
     }
+
+    @Override
+    public Properties getProperties() {
+        Properties p = new Properties();
+        if (source.getSourceNodes().size() > 0) {
+            for (InputNode n : source.getSourceNodes()) {
+                p.add(n.getProperties());
+            }
+        } else {
+            p.setProperty("name", "Slot");
+            p.setProperty("figure", figure.getProperties().get("name"));
+            p.setProperty("connectionCount", Integer.toString(connections.size()));
+        }
+        return p;
+    }
     public static final Comparator<Slot> slotIndexComparator = new Comparator<Slot>() {
 
+        @Override
         public int compare(Slot o1, Slot o2) {
             return o1.wantedIndex - o2.wantedIndex;
         }
     };
     public static final Comparator<Slot> slotFigureComparator = new Comparator<Slot>() {
 
+        @Override
         public int compare(Slot o1, Slot o2) {
             return o1.figure.getId() - o2.figure.getId();
         }
     };
 
+    public InputNode getAssociatedNode() {
+        return associatedNode;
+    }
+
+    public void setAssociatedNode(InputNode node) {
+        associatedNode = node;
+    }
+
+    public int getWidth() {
+        if (shortName == null || shortName.length() <= 1) {
+            return Figure.SLOT_WIDTH;
+        } else {
+            BufferedImage image = new BufferedImage(1, 1, BufferedImage.TYPE_INT_RGB);
+            Graphics g = image.getGraphics();
+            g.setFont(figure.getDiagram().getSlotFont().deriveFont(Font.BOLD));
+            FontMetrics metrics = g.getFontMetrics();
+            return Math.max(Figure.SLOT_WIDTH, metrics.stringWidth(shortName) + 6);
+        }
+    }
+
     public int getWantedIndex() {
         return wantedIndex;
     }
 
+    @Override
     public Source getSource() {
         return source;
     }
 
-    public String getName() {
-        return name;
+    public String getText() {
+        return text;
     }
 
     public void setShortName(String s) {
         assert s != null;
-        assert s.length() <= 2;
+//        assert s.length() <= 2;
         this.shortName = s;
 
     }
@@ -88,15 +136,27 @@
         return shortName;
     }
 
-    public boolean getShowName() {
+    public String getToolTipText() {
+        StringBuilder sb = new StringBuilder();
+        sb.append(text);
+
+        for (InputNode n : getSource().getSourceNodes()) {
+            sb.append("Node (ID=" + n.getId() + "): " + n.getProperties().get("name"));
+            sb.append("<br>");
+        }
+
+        return sb.toString();
+    }
+
+    public boolean shouldShowName() {
         return getShortName() != null && getShortName().length() > 0;
     }
 
-    public void setName(String s) {
+    public void setText(String s) {
         if (s == null) {
             s = "";
         }
-        this.name = s;
+        this.text = s;
     }
 
     public Figure getFigure() {
@@ -104,17 +164,26 @@
         return figure;
     }
 
+    public Color getColor() {
+        return this.color;
+    }
+
+    public void setColor(Color c) {
+        color = c;
+    }
+
     public List<Connection> getConnections() {
         return Collections.unmodifiableList(connections);
     }
 
     public void removeAllConnections() {
-        List<Connection> connectionsCopy = new ArrayList<Connection>(this.connections);
+        List<Connection> connectionsCopy = new ArrayList<>(this.connections);
         for (Connection c : connectionsCopy) {
             c.remove();
         }
     }
 
+    @Override
     public Vertex getVertex() {
         return figure;
     }
@@ -123,3 +192,4 @@
 
     public abstract void setPosition(int position);
 }
+
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/Source.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,100 +0,0 @@
-/*
- * Copyright (c) 2008, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- *
- */
-package com.sun.hotspot.igv.graph;
-
-import com.sun.hotspot.igv.data.InputBlock;
-import com.sun.hotspot.igv.data.InputGraph;
-import com.sun.hotspot.igv.data.InputNode;
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Set;
-
-/**
- *
- * @author Thomas Wuerthinger
- */
-public class Source {
-
-    private List<InputNode> sourceNodes;
-    private Set<Integer> set;
-
-    public Source() {
-        sourceNodes = new ArrayList<InputNode>(1);
-    }
-
-    public List<InputNode> getSourceNodes() {
-        return Collections.unmodifiableList(sourceNodes);
-    }
-
-    public Set<Integer> getSourceNodesAsSet() {
-        if (set == null) {
-            set = new HashSet<Integer>();
-            for (InputNode n : sourceNodes) {
-                int id = n.getId();
-                //if(id < 0) id = -id;
-                set.add(id);
-            }
-        }
-        return set;
-    }
-
-    public void addSourceNode(InputNode n) {
-        sourceNodes.add(n);
-        set = null;
-    }
-
-    public void removeSourceNode(InputNode n) {
-        sourceNodes.remove(n);
-        set = null;
-    }
-
-    public interface Provider {
-
-        public Source getSource();
-    }
-
-    public void setSourceNodes(List<InputNode> sourceNodes) {
-        this.sourceNodes = sourceNodes;
-        set = null;
-    }
-
-    public void addSourceNodes(Source s) {
-        for (InputNode n : s.getSourceNodes()) {
-            sourceNodes.add(n);
-        }
-        set = null;
-    }
-
-    public boolean isInBlock(InputGraph g, InputBlock blockNode) {
-
-        for (InputNode n : this.getSourceNodes()) {
-            if (g.getBlock(n) == blockNode) {
-                return true;
-            }
-        }
-        return false;
-    }
-}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/SuccessorSelector.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/SuccessorSelector.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -38,9 +38,10 @@
         this.innerSelector = innerSelector;
     }
 
+    @Override
     public List<Figure> selected(Diagram d) {
         List<Figure> inner = innerSelector.selected(d);
-        List<Figure> result = new ArrayList<Figure>();
+        List<Figure> result = new ArrayList<>();
         for (Figure f : d.getFigures()) {
             boolean saved = false;
             for (Figure f2 : f.getPredecessors()) {
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Graph/src/com/sun/hotspot/igv/graph/services/DiagramProvider.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,38 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+
+package com.sun.hotspot.igv.graph.services;
+
+import com.sun.hotspot.igv.data.ChangedEvent;
+import com.sun.hotspot.igv.graph.Diagram;
+
+/**
+ *
+ * @author Thomas Wuerthinger
+ */
+public interface DiagramProvider {
+    Diagram getDiagram();
+    ChangedEvent<DiagramProvider> getChangedEvent();
+
+}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/nbproject/project.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/nbproject/project.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,2 +1,2 @@
-javac.source=1.5
-javac.compilerargs=-Xlint -Xlint:-serial
+javac.source=1.7
+javac.compilerargs=-Xlint -Xlint:-serial
--- a/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/ClusterEdge.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/ClusterEdge.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -60,4 +60,8 @@
     public List<Point> getControlPoints() {
         return points;
     }
+
+    public boolean isVIP() {
+        return false;
+    }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/ClusterIngoingConnection.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/ClusterIngoingConnection.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -73,4 +73,8 @@
     public List<Point> getControlPoints() {
         return controlPoints;
     }
+
+    public boolean isVIP() {
+        return false;
+    }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/ClusterInputSlotNode.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/ClusterInputSlotNode.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
--- a/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/ClusterNode.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/ClusterNode.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -93,7 +93,7 @@
         outputSlot = new Port() {
 
             public Point getRelativePosition() {
-                return new Point(size.width / 2, size.height);
+                return new Point(size.width / 2, 0);//size.height);
             }
 
             public Vertex getVertex() {
@@ -183,7 +183,7 @@
 
         for (Link e : subEdges) {
             List<Point> arr = e.getControlPoints();
-            ArrayList<Point> newArr = new ArrayList<Point>();
+            ArrayList<Point> newArr = new ArrayList<Point>(arr.size());
             for (Point p : arr) {
                 if (p != null) {
                     Point p2 = new Point(p);
--- a/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/ClusterOutgoingConnection.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/ClusterOutgoingConnection.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -65,4 +65,8 @@
     public List<Point> getControlPoints() {
         return intermediatePoints;
     }
+
+    public boolean isVIP() {
+        return false;
+    }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/ClusterOutputSlotNode.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/ClusterOutputSlotNode.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -88,7 +88,7 @@
             public Point getRelativePosition() {
                 Point p = new Point(thisNode.getPosition());
                 p.x += ClusterNode.BORDER;
-                p.y = thisBlockNode.getSize().height;
+                p.y = 0;//thisBlockNode.getSize().height;
                 return p;
             }
 
--- a/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/Edge.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/Edge.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -83,6 +83,7 @@
         dest.addInEdge(this);
     }
 
+    @Override
     public String toString() {
         return "Edge (" + source + " -- " + dest + "): " + data;
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/Graph.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/Graph.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,13 +23,7 @@
  */
 package com.sun.hotspot.igv.hierarchicallayout;
 
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.Queue;
+import java.util.*;
 
 /**
  *
@@ -42,13 +36,13 @@
     private List<Node<N, E>> nodeList;
 
     public Graph() {
-        nodes = new HashMap<Object, Node<N, E>>();
-        edges = new HashMap<Object, Edge<N, E>>();
-        nodeList = new ArrayList<Node<N, E>>();
+        nodes = new HashMap<>();
+        edges = new HashMap<>();
+        nodeList = new ArrayList<>();
     }
 
     public Node<N, E> createNode(N data, Object key) {
-        Node<N, E> n = new Node<N, E>(this, data);
+        Node<N, E> n = new Node<>(this, data);
         assert key == null || !nodes.containsKey(key);
         if (key != null) {
             nodes.put(key, n);
@@ -58,7 +52,7 @@
     }
 
     public Edge<N, E> createEdge(Node<N, E> source, Node<N, E> dest, E data, Object key) {
-        Edge<N, E> e = new Edge<N, E>(this, source, dest, data);
+        Edge<N, E> e = new Edge<>(this, source, dest, data);
         source.addOutEdge(e);
         dest.addInEdge(e);
         if (key != null) {
@@ -114,7 +108,7 @@
 
     public List<Node<N, E>> getNodesWithInDegree(int x, boolean countSelfLoops) {
 
-        List<Node<N, E>> result = new ArrayList<Node<N, E>>();
+        List<Node<N, E>> result = new ArrayList<>();
         for (Node<N, E> n : getNodes()) {
             if (n.getInDegree(countSelfLoops) == x) {
                 result.add(n);
@@ -126,7 +120,7 @@
     }
 
     private void markReachable(Node<N, E> startingNode) {
-        ArrayList<Node<N, E>> arr = new ArrayList<Node<N, E>>();
+        ArrayList<Node<N, E>> arr = new ArrayList<>();
         arr.add(startingNode);
         for (Node<N, E> n : getNodes()) {
             n.setReachable(false);
@@ -151,7 +145,7 @@
             n.setActive(false);
         }
 
-        Queue<Node<N, E>> queue = new LinkedList<Node<N, E>>();
+        Queue<Node<N, E>> queue = new LinkedList<>();
         queue.add(startingNode);
         startingNode.setVisited(true);
         int layer = 0;
--- a/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/HierarchicalClusterLayoutManager.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/HierarchicalClusterLayoutManager.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -44,12 +44,12 @@
  */
 public class HierarchicalClusterLayoutManager implements LayoutManager {
 
-    private OldHierarchicalLayoutManager.Combine combine;
-    private LayoutManager subManager = new OldHierarchicalLayoutManager(combine);
-    private LayoutManager manager = new OldHierarchicalLayoutManager(combine, 150);
+    private HierarchicalLayoutManager.Combine combine;
+    private LayoutManager subManager = new HierarchicalLayoutManager(combine);
+    private LayoutManager manager = new HierarchicalLayoutManager(combine);
     private static final boolean TRACE = false;
 
-    public HierarchicalClusterLayoutManager(OldHierarchicalLayoutManager.Combine combine) {
+    public HierarchicalClusterLayoutManager(HierarchicalLayoutManager.Combine combine) {
         this.combine = combine;
     }
 
@@ -57,6 +57,10 @@
         doLayout(graph, new HashSet<Vertex>(), new HashSet<Vertex>(), new HashSet<Link>());
     }
 
+    public void doLayout(LayoutGraph graph, Set<? extends Link> importantLinks) {
+        doLayout(graph);
+    }
+
     public void setSubManager(LayoutManager manager) {
         this.subManager = manager;
     }
@@ -116,7 +120,7 @@
 
         for (Vertex v : graph.getVertices()) {
             Cluster c = v.getCluster();
-            assert c != null;
+            assert c != null : "Cluster of vertex " + v + " is null!";
             clusterNodes.get(c).addSubNode(v);
         }
 
@@ -130,9 +134,9 @@
             Cluster toCluster = toVertex.getCluster();
 
             Port samePort = null;
-            if (combine == OldHierarchicalLayoutManager.Combine.SAME_INPUTS) {
+            if (combine == HierarchicalLayoutManager.Combine.SAME_INPUTS) {
                 samePort = toPort;
-            } else if (combine == OldHierarchicalLayoutManager.Combine.SAME_OUTPUTS) {
+            } else if (combine == HierarchicalLayoutManager.Combine.SAME_OUTPUTS) {
                 samePort = fromPort;
             }
 
@@ -196,7 +200,7 @@
 
         for (Cluster c : cluster) {
             ClusterNode n = clusterNodes.get(c);
-            subManager.doLayout(new LayoutGraph(n.getSubEdges(), n.getSubNodes()), clusterInputSlotSet.get(c), clusterOutputSlotSet.get(c), new HashSet<Link>());
+            subManager.doLayout(new LayoutGraph(n.getSubEdges(), n.getSubNodes()), new HashSet<Link>());
             n.updateSize();
         }
 
@@ -206,7 +210,7 @@
             ((ClusterNode) v).setRoot(true);
         }
 
-        manager.doLayout(new LayoutGraph(clusterEdges, clusterNodeSet), new HashSet<Vertex>(), new HashSet<Vertex>(), interClusterEdges);
+        manager.doLayout(new LayoutGraph(clusterEdges, clusterNodeSet), interClusterEdges);
 
         for (Cluster c : cluster) {
             ClusterNode n = clusterNodes.get(c);
--- a/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/HierarchicalLayoutManager.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/HierarchicalLayoutManager.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -29,18 +29,7 @@
 import com.sun.hotspot.igv.layout.Vertex;
 import java.awt.Dimension;
 import java.awt.Point;
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.Comparator;
-import java.util.HashSet;
-import java.util.HashMap;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.Queue;
-import java.util.Set;
-import java.util.SortedSet;
-import java.util.Stack;
-import java.util.TreeSet;
+import java.util.*;
 
 /**
  *
@@ -54,10 +43,11 @@
     public static final int CROSSING_ITERATIONS = 2;
     public static final int DUMMY_HEIGHT = 1;
     public static final int DUMMY_WIDTH = 1;
-    public static final int X_OFFSET = 9;
-    public static final int LAYER_OFFSET = 30;
+    public static final int X_OFFSET = 8;
+    public static final int LAYER_OFFSET = 8;
     public static final int MAX_LAYER_LENGTH = -1;
     public static final int MIN_LAYER_DIFFERENCE = 1;
+    public static final int VIP_BONUS = 10;
 
     public enum Combine {
 
@@ -85,8 +75,6 @@
     private LayoutGraph graph;
     private List<LayoutNode>[] layers;
     private int layerCount;
-    private Set<? extends Vertex> firstLayerHint;
-    private Set<? extends Vertex> lastLayerHint;
     private Set<? extends Link> importantLinks;
     private Set<Link> linksToFollow;
 
@@ -101,11 +89,13 @@
         public int yOffset;
         public int bottomYOffset;
         public Vertex vertex; // Only used for non-dummy nodes, otherwise null
-        public List<LayoutEdge> preds = new ArrayList<LayoutEdge>();
-        public List<LayoutEdge> succs = new ArrayList<LayoutEdge>();
-        public HashMap<Integer, Integer> outOffsets = new HashMap<Integer, Integer>();
-        public HashMap<Integer, Integer> inOffsets = new HashMap<Integer, Integer>();
+
+        public List<LayoutEdge> preds = new ArrayList<>();
+        public List<LayoutEdge> succs = new ArrayList<>();
+        public HashMap<Integer, Integer> outOffsets = new HashMap<>();
+        public HashMap<Integer, Integer> inOffsets = new HashMap<>();
         public int pos = -1; // Position within layer
+
         public int crossingNumber;
 
         @Override
@@ -121,6 +111,7 @@
         public int relativeFrom;
         public int relativeTo;
         public Link link;
+        public boolean vip;
     }
 
     private abstract class AlgorithmPart {
@@ -171,7 +162,7 @@
         this.layerOffset = LAYER_OFFSET;
         this.maxLayerLength = MAX_LAYER_LENGTH;
         this.minLayerDifference = MIN_LAYER_DIFFERENCE;
-        this.linksToFollow = new HashSet<Link>();
+        this.linksToFollow = new HashSet<>();
     }
 
     public int getMaxLayerLength() {
@@ -186,26 +177,26 @@
         minLayerDifference = v;
     }
 
+    @Override
     public void doLayout(LayoutGraph graph) {
-        doLayout(graph, new HashSet<Vertex>(), new HashSet<Vertex>(), new HashSet<Link>());
+        doLayout(graph, new HashSet<Link>());
 
     }
 
-    public void doLayout(LayoutGraph graph, Set<? extends Vertex> firstLayerHint, Set<? extends Vertex> lastLayerHint, Set<? extends Link> importantLinks) {
+    @Override
+    public void doLayout(LayoutGraph graph, Set<? extends Link> importantLinks) {
 
         this.importantLinks = importantLinks;
         this.graph = graph;
-        this.firstLayerHint = firstLayerHint;
-        this.lastLayerHint = lastLayerHint;
 
-        vertexToLayoutNode = new HashMap<Vertex, LayoutNode>();
-        reversedLinks = new HashSet<Link>();
-        reversedLinkStartPoints = new HashMap<Link, List<Point>>();
-        reversedLinkEndPoints = new HashMap<Link, List<Point>>();
-        bottomEdgeHash = new HashMap<LayoutEdge, LayoutEdge>();
-        nodes = new ArrayList<LayoutNode>();
-        splitStartPoints = new HashMap<Link, List<Point>>();
-        splitEndPoints = new HashMap<Link, List<Point>>();
+        vertexToLayoutNode = new HashMap<>();
+        reversedLinks = new HashSet<>();
+        reversedLinkStartPoints = new HashMap<>();
+        reversedLinkEndPoints = new HashMap<>();
+        bottomEdgeHash = new HashMap<>();
+        nodes = new ArrayList<>();
+        splitStartPoints = new HashMap<>();
+        splitEndPoints = new HashMap<>();
 
         // #############################################################
         // Step 1: Build up data structure
@@ -216,7 +207,7 @@
         new ReverseEdges().start();
 
         for (LayoutNode n : nodes) {
-            ArrayList<LayoutEdge> tmpArr = new ArrayList<LayoutEdge>();
+            ArrayList<LayoutEdge> tmpArr = new ArrayList<>();
             for (LayoutEdge e : n.succs) {
                 if (importantLinks.contains(e.link)) {
                     tmpArr.add(e);
@@ -224,7 +215,6 @@
             }
 
             for (LayoutEdge e : tmpArr) {
-                //System.out.println("Removed " + e);
                 e.from.succs.remove(e);
                 e.to.preds.remove(e);
             }
@@ -244,8 +234,7 @@
 
         // #############################################################
         // STEP 7: Assign X coordinates
-        //new AssignXCoordinates().start();
-        new AssignXCoordinates2().start();
+        new AssignXCoordinates().start();
 
         // #############################################################
         // STEP 6: Assign Y coordinates
@@ -260,10 +249,11 @@
 
         private int pointCount;
 
+        @Override
         protected void run() {
 
-            HashMap<Vertex, Point> vertexPositions = new HashMap<Vertex, Point>();
-            HashMap<Link, List<Point>> linkPositions = new HashMap<Link, List<Point>>();
+            HashMap<Vertex, Point> vertexPositions = new HashMap<>();
+            HashMap<Link, List<Point>> linkPositions = new HashMap<>();
             for (Vertex v : graph.getVertices()) {
                 LayoutNode n = vertexToLayoutNode.get(v);
                 assert !vertexPositions.containsKey(v);
@@ -274,12 +264,12 @@
 
                 for (LayoutEdge e : n.preds) {
                     if (e.link != null) {
-                        ArrayList<Point> points = new ArrayList<Point>();
+                        ArrayList<Point> points = new ArrayList<>();
 
-                        Point p = new Point(e.to.x + e.relativeTo, e.to.y + e.to.yOffset);
+                        Point p = new Point(e.to.x + e.relativeTo, e.to.y + e.to.yOffset + e.link.getTo().getRelativePosition().y);
                         points.add(p);
                         if (e.to.inOffsets.containsKey(e.relativeTo)) {
-                            points.add(new Point(p.x, p.y + e.to.inOffsets.get(e.relativeTo)));
+                            points.add(new Point(p.x, p.y + e.to.inOffsets.get(e.relativeTo) + e.link.getTo().getRelativePosition().y));
                         }
 
                         LayoutNode cur = e.from;
@@ -299,16 +289,14 @@
                             cur = curEdge.from;
                         }
 
-                        p = new Point(cur.x + curEdge.relativeFrom, cur.y + cur.height - cur.bottomYOffset);
+                        p = new Point(cur.x + curEdge.relativeFrom, cur.y + cur.height - cur.bottomYOffset + (curEdge.link == null ? 0 : curEdge.link.getFrom().getRelativePosition().y));
                         if (curEdge.from.outOffsets.containsKey(curEdge.relativeFrom)) {
-                            points.add(new Point(p.x, p.y + curEdge.from.outOffsets.get(curEdge.relativeFrom)));
+                            points.add(new Point(p.x, p.y + curEdge.from.outOffsets.get(curEdge.relativeFrom) + (curEdge.link == null ? 0 : curEdge.link.getFrom().getRelativePosition().y)));
                         }
                         points.add(p);
 
                         Collections.reverse(points);
 
-
-
                         if (cur.vertex == null && cur.preds.size() == 0) {
 
                             if (reversedLinkEndPoints.containsKey(e.link)) {
@@ -359,17 +347,17 @@
 
                 for (LayoutEdge e : n.succs) {
                     if (e.link != null) {
-                        ArrayList<Point> points = new ArrayList<Point>();
-                        Point p = new Point(e.from.x + e.relativeFrom, e.from.y + e.from.height - e.from.bottomYOffset);
+                        ArrayList<Point> points = new ArrayList<>();
+                        Point p = new Point(e.from.x + e.relativeFrom, e.from.y + e.from.height - e.from.bottomYOffset + e.link.getFrom().getRelativePosition().y);
                         points.add(p);
                         if (e.from.outOffsets.containsKey(e.relativeFrom)) {
-                            points.add(new Point(p.x, p.y + e.from.outOffsets.get(e.relativeFrom)));
+                            points.add(new Point(p.x, p.y + e.from.outOffsets.get(e.relativeFrom) + e.link.getFrom().getRelativePosition().y));
                         }
 
                         LayoutNode cur = e.to;
                         LayoutNode other = e.from;
                         LayoutEdge curEdge = e;
-                        while (cur.vertex == null && cur.succs.size() != 0) {
+                        while (cur.vertex == null && !cur.succs.isEmpty()) {
                             if (points.size() > 1 && points.get(points.size() - 1).x == cur.x + cur.width / 2 && points.get(points.size() - 2).x == cur.x + cur.width / 2) {
                                 points.remove(points.size() - 1);
                             }
@@ -378,7 +366,7 @@
                                 points.remove(points.size() - 1);
                             }
                             points.add(new Point(cur.x + cur.width / 2, cur.y + cur.height));
-                            if (cur.succs.size() == 0) {
+                            if (cur.succs.isEmpty()) {
                                 break;
                             }
                             assert cur.succs.size() == 1;
@@ -386,15 +374,13 @@
                             cur = curEdge.to;
                         }
 
-
-                        p = new Point(cur.x + curEdge.relativeTo, cur.y + cur.yOffset);
+                        p = new Point(cur.x + curEdge.relativeTo, cur.y + cur.yOffset + ((curEdge.link == null) ? 0 : curEdge.link.getTo().getRelativePosition().y));
                         points.add(p);
                         if (curEdge.to.inOffsets.containsKey(curEdge.relativeTo)) {
-                            points.add(new Point(p.x, p.y + curEdge.to.inOffsets.get(curEdge.relativeTo)));
+                            points.add(new Point(p.x, p.y + curEdge.to.inOffsets.get(curEdge.relativeTo) + ((curEdge.link == null) ? 0 : curEdge.link.getTo().getRelativePosition().y)));
                         }
 
-
-                        if (cur.succs.size() == 0 && cur.vertex == null) {
+                        if (cur.succs.isEmpty() && cur.vertex == null) {
                             if (reversedLinkStartPoints.containsKey(e.link)) {
                                 for (Point p1 : reversedLinkStartPoints.get(e.link)) {
                                     points.add(0, new Point(p1.x + other.x, p1.y + other.y));
@@ -495,13 +481,14 @@
 
         public float d;
         public int orderNumber = -1;
-        public ArrayList<LayoutNode> nodes = new ArrayList<LayoutNode>();
-        public HashSet<Segment> succs = new HashSet<Segment>();
-        public HashSet<Segment> preds = new HashSet<Segment>();
+        public ArrayList<LayoutNode> nodes = new ArrayList<>();
+        public HashSet<Segment> succs = new HashSet<>();
+        public HashSet<Segment> preds = new HashSet<>();
         public Region region;
     }
     private static final Comparator<Segment> segmentComparator = new Comparator<Segment>() {
 
+        @Override
         public int compare(Segment s1, Segment s2) {
             return s1.orderNumber - s2.orderNumber;
         }
@@ -511,26 +498,46 @@
 
         public float d;
         public int minOrderNumber;
-        public SortedSet<Segment> segments = new TreeSet<Segment>(segmentComparator);
-        public HashSet<Region> succs = new HashSet<Region>(4);
-        public HashSet<Region> preds = new HashSet<Region>(4);
+        public SortedSet<Segment> segments = new TreeSet<>(segmentComparator);
+        public HashSet<Region> succs = new HashSet<>(4);
+        public HashSet<Region> preds = new HashSet<>(4);
     }
     private static final Comparator<Region> regionComparator = new Comparator<Region>() {
 
+        @Override
         public int compare(Region r1, Region r2) {
             return r1.minOrderNumber - r2.minOrderNumber;
         }
     };
     private static final Comparator<LayoutNode> nodePositionComparator = new Comparator<LayoutNode>() {
 
+        @Override
         public int compare(LayoutNode n1, LayoutNode n2) {
             return n1.pos - n2.pos;
         }
     };
     private static final Comparator<LayoutNode> nodeProcessingDownComparator = new Comparator<LayoutNode>() {
-
+        @Override
         public int compare(LayoutNode n1, LayoutNode n2) {
+            int n1VIP = 0;
+            for (LayoutEdge e : n1.preds) {
+                if (e.vip) {
+                    n1VIP++;
+                }
+            }
+            int n2VIP = 0;
+            for (LayoutEdge e : n2.preds) {
+                if (e.vip) {
+                    n2VIP++;
+                }
+            }
+            if (n1VIP != n2VIP) {
+                return n2VIP - n1VIP;
+            }
             if (n1.vertex == null) {
+                if (n2.vertex == null) {
+                    return 0;
+                }
                 return -1;
             }
             if (n2.vertex == null) {
@@ -541,8 +548,27 @@
     };
     private static final Comparator<LayoutNode> nodeProcessingUpComparator = new Comparator<LayoutNode>() {
 
+        @Override
         public int compare(LayoutNode n1, LayoutNode n2) {
+            int n1VIP = 0;
+            for (LayoutEdge e : n1.succs) {
+                if (e.vip) {
+                    n1VIP++;
+                }
+            }
+            int n2VIP = 0;
+            for (LayoutEdge e : n2.succs) {
+                if (e.vip) {
+                    n2VIP++;
+                }
+            }
+            if (n1VIP != n2VIP) {
+                return n2VIP - n1VIP;
+            }
             if (n1.vertex == null) {
+                if (n2.vertex == null) {
+                    return 0;
+                }
                 return -1;
             }
             if (n2.vertex == null) {
@@ -552,7 +578,7 @@
         }
     };
 
-    private class AssignXCoordinates2 extends AlgorithmPart {
+    private class AssignXCoordinates extends AlgorithmPart {
 
         private ArrayList<Integer>[] space;
         private ArrayList<LayoutNode>[] downProcessingOrder;
@@ -564,16 +590,21 @@
             }
         }
 
-        protected void run() {
-
+        @SuppressWarnings("unchecked")
+        private void createArrays() {
             space = new ArrayList[layers.length];
             downProcessingOrder = new ArrayList[layers.length];
             upProcessingOrder = new ArrayList[layers.length];
+        }
+
+        @Override
+        protected void run() {
+            createArrays();
 
             for (int i = 0; i < layers.length; i++) {
-                space[i] = new ArrayList<Integer>();
-                downProcessingOrder[i] = new ArrayList<LayoutNode>();
-                upProcessingOrder[i] = new ArrayList<LayoutNode>();
+                space[i] = new ArrayList<>();
+                downProcessingOrder[i] = new ArrayList<>();
+                upProcessingOrder[i] = new ArrayList<>();
 
                 int curX = 0;
                 for (LayoutNode n : layers[i]) {
@@ -590,72 +621,106 @@
             initialPositions();
             for (int i = 0; i < SWEEP_ITERATIONS; i++) {
                 sweepDown();
-                sweepUp();
+                adjustSpace();
+                sweepUp(false);
+                adjustSpace();
             }
 
-            for (int i = 0; i < SWEEP_ITERATIONS; i++) {
-                doubleSweep();
+            sweepDown();
+            adjustSpace();
+            sweepUp(true);
+        }
+
+        private void adjustSpace() {
+            for (int i = 0; i < layers.length; i++) {
+                //               space[i] = new ArrayList<>();
+                int curX = 0;
+                for (LayoutNode n : layers[i]) {
+                    space[i].add(n.x);
+//                    curX += n.width + xOffset;
+                }
             }
         }
 
         private int calculateOptimalDown(LayoutNode n) {
-
-            List<Integer> values = new ArrayList<Integer>();
-            if (n.preds.size() == 0) {
+            int size = n.preds.size();
+            if (size == 0) {
                 return n.x;
             }
+            int vipCount = 0;
             for (LayoutEdge e : n.preds) {
-                int cur = e.from.x + e.relativeFrom - e.relativeTo;
-                values.add(cur);
+                if (e.vip) {
+                    vipCount++;
+                }
             }
-            return median(values);
+
+            if (vipCount == 0) {
+                int[] values = new int[size];
+                for (int i = 0; i < size; i++) {
+                    LayoutEdge e = n.preds.get(i);
+                    values[i] = e.from.x + e.relativeFrom - e.relativeTo;
+                }
+                return median(values);
+            } else {
+                int z = 0;
+                int[] values = new int[vipCount];
+                for (int i = 0; i < size; i++) {
+                    LayoutEdge e = n.preds.get(i);
+                    if (e.vip) {
+                        values[z++] = e.from.x + e.relativeFrom - e.relativeTo;
+                    }
+                }
+                return median(values);
+            }
         }
 
         private int calculateOptimalBoth(LayoutNode n) {
-
-            List<Integer> values = new ArrayList<Integer>();
-            if (n.preds.size() == 0 + n.succs.size()) {
+            if (n.preds.size() == n.succs.size()) {
                 return n.x;
             }
+
+            int[] values = new int[n.preds.size() + n.succs.size()];
+            int i = 0;
+
             for (LayoutEdge e : n.preds) {
-                int cur = e.from.x + e.relativeFrom - e.relativeTo;
-                values.add(cur);
+                values[i] = e.from.x + e.relativeFrom - e.relativeTo;
+                i++;
             }
 
             for (LayoutEdge e : n.succs) {
-                int cur = e.to.x + e.relativeTo - e.relativeFrom;
-                values.add(cur);
+                values[i] = e.to.x + e.relativeTo - e.relativeFrom;
+                i++;
             }
 
             return median(values);
         }
 
         private int calculateOptimalUp(LayoutNode n) {
-
-            //List<Integer> values = new ArrayList<Integer>();
             int size = n.succs.size();
             if (size == 0) {
                 return n.x;
+            }
+            int[] values = new int[size];
+            for (int i = 0; i < size; i++) {
+                LayoutEdge e = n.succs.get(i);
+                values[i] = e.to.x + e.relativeTo - e.relativeFrom;
+                if (e.vip) {
+                    return values[i];
+                }
+            }
+            return median(values);
+        }
+
+        private int median(int[] values) {
+            Arrays.sort(values);
+            if (values.length % 2 == 0) {
+                return (values[values.length / 2 - 1] + values[values.length / 2]) / 2;
             } else {
-                int result = 0;
-                for (LayoutEdge e : n.succs) {
-                    int cur = e.to.x + e.relativeTo - e.relativeFrom;
-                    result += cur;
-                }
-                return result / size; //median(values);
+                return values[values.length / 2];
             }
         }
 
-        private int median(List<Integer> values) {
-            Collections.sort(values);
-            if (values.size() % 2 == 0) {
-                return (values.get(values.size() / 2 - 1) + values.get(values.size() / 2)) / 2;
-            } else {
-                return values.get(values.size() / 2);
-            }
-        }
-
-        private void sweepUp() {
+        private void sweepUp(boolean onlyDummies) {
             for (int i = layers.length - 1; i >= 0; i--) {
                 NodeRow r = new NodeRow(space[i]);
                 for (LayoutNode n : upProcessingOrder[i]) {
@@ -663,14 +728,6 @@
                     r.insert(n, optimal);
                 }
             }
-        /*
-        for(int i=0; i<layers.length; i++) {
-        NodeRow r = new NodeRow(space[i]);
-        for(LayoutNode n : upProcessingOrder[i]) {
-        int optimal = calculateOptimalUp(n);
-        r.insert(n, optimal);
-        }
-        }*/
         }
 
         private void doubleSweep() {
@@ -700,7 +757,7 @@
         private ArrayList<Integer> space;
 
         public NodeRow(ArrayList<Integer> space) {
-            treeSet = new TreeSet<LayoutNode>(nodePositionComparator);
+            treeSet = new TreeSet<>(nodePositionComparator);
             this.space = space;
         }
 
@@ -739,357 +796,15 @@
                     n.x = pos;
                 }
 
-                assert minX <= maxX;
+                assert minX <= maxX : minX + " vs " + maxX;
             }
 
             treeSet.add(n);
         }
     }
-
-    private class AssignXCoordinates extends AlgorithmPart {
-
-        HashMap<LayoutNode, Segment> hashMap = new HashMap<LayoutNode, Segment>();
-        ArrayList<Segment> segments = new ArrayList<Segment>();
-
-        private void generateSegments() {
-
-            for (int i = 0; i < layerCount; i++) {
-                for (LayoutNode n : layers[i]) {
-                    if (!hashMap.containsKey(n)) {
-                        Segment s = new Segment();
-                        segments.add(s);
-                        LayoutNode curNode = n;
-
-                        int maxLength = 0;
-                        while (curNode.succs.size() == 1 && curNode.preds.size() == 1) {
-                            s.nodes.add(curNode);
-                            assert !hashMap.containsKey(curNode);
-                            hashMap.put(curNode, s);
-                            curNode = curNode.succs.get(0).to;
-                            maxLength++;
-                        //if(maxLength > 10) break;
-                        }
-
-                        if (s.nodes.size() > 0 && curNode.preds.size() == 1 && curNode.vertex == null) {
-                            s.nodes.add(curNode);
-                            assert !hashMap.containsKey(curNode);
-                            hashMap.put(curNode, s);
-                        }
-
-                        if (s.nodes.size() == 0) {
-                            // Simple segment with a single node
-                            s.nodes.add(n);
-                            hashMap.put(n, s);
-                        }
-                    }
-                }
-            }
-        }
-
-        private void addEdges() {
-
-            for (int i = 0; i < layerCount; i++) {
-                LayoutNode prev = null;
-                for (LayoutNode n : layers[i]) {
-
-                    if (prev != null) {
-                        Segment s1 = hashMap.get(prev);
-                        Segment s2 = hashMap.get(n);
-
-                        if (s1 != s2) {
-                            s1.succs.add(s2);
-                            s2.preds.add(s1);
-                        }
-                    }
-                    prev = n;
-
-                }
-            }
-        }
-
-        private void topologicalSorting() {
-
-            Queue<Segment> queue = new LinkedList<Segment>();
-
-            int index = 0;
-            ArrayList<Segment> newList = new ArrayList<Segment>();
-            for (Segment s : segments) {
-                if (s.preds.size() == 0) {
-                    s.orderNumber = index;
-                    newList.add(s);
-                    index++;
-                    queue.add(s);
-                }
-            }
-
-            while (!queue.isEmpty()) {
-                Segment s = queue.remove();
-
-                for (Segment succ : s.succs) {
-                    succ.preds.remove(s);
-                    if (succ.preds.size() == 0) {
-                        queue.add(succ);
-                        succ.orderNumber = index;
-                        newList.add(succ);
-                        index++;
-                    }
-                }
-            }
-
-            segments = newList;
-        }
-
-        private void initialPositions() {
-
-            int[] minPos = new int[layers.length];
-
-            for (Segment s : segments) {
-                int max = 0;
-                for (LayoutNode n : s.nodes) {
-                    int x = minPos[n.layer];
-                    if (x > max) {
-                        max = x;
-                    }
-                }
-
-                for (LayoutNode n : s.nodes) {
-                    minPos[n.layer] = max + n.width + xOffset;
-                    n.x = max;
-                }
-            }
-        }
-
-        private int predSum(LayoutNode n) {
-            int sum = 0;
-            for (LayoutEdge e : n.preds) {
-                assert e.to == n;
-                //sum += (e.from.x + e.relativeFrom + (int)hashMap.get(e.from).d) - (e.to.x + e.relativeTo + (int)hashMap.get(e.to).d);
-                sum += (e.from.x + e.relativeFrom) - (e.to.x + e.relativeTo);
-            }
-
-            return sum;
-        }
-
-        private int succSum(LayoutNode n) {
-            int sum = 0;
-            for (LayoutEdge e : n.succs) {
-
-                assert e.from == n;
-                sum += (e.to.x + e.relativeTo) - (e.from.x + e.relativeFrom);
-            //sum += (e.to.x + e.relativeTo + (int)hashMap.get(e.to).d) - (e.from.x + e.relativeFrom + (int)hashMap.get(e.from).d);
-            }
-
-            return sum;
-
-        }
-
-        private void downValues() {
-
-            for (Segment s : segments) {
-                downValues(s);
-
-            }
-
-        }
-
-        private void downValues(Segment s) {
-            LayoutNode n = s.nodes.get(0); // Only first node needed, all other have same coordinate
-
-            if (n.preds.size() == 0) {
-                // Value is 0.0;
-                if (n.succs.size() == 0) {
-                    s.d = 0.0f;
-                } else {
-                    s.d = (((float) succSum(n) / (float) n.succs.size())) / 2;
-                }
-            } else {
-                s.d = (float) predSum(n) / (float) n.preds.size();
-            }
-        }
-
-        private void upValues() {
-            for (Segment s : segments) {
-                upValues(s);
-            }
-        }
-
-        private void upValues(Segment s) {
-            LayoutNode n = s.nodes.get(0); // Only first node needed, all other have same coordinate
-
-            if (n.succs.size() == 0) {
-                // Value is 0.0;
-                if (n.preds.size() == 0) {
-                    s.d = 0.0f;
-                } else {
-                    s.d = (float) predSum(n) / (float) n.preds.size();
-                }
-            } else {
-                s.d = ((float) succSum(n) / (float) n.succs.size()) / 2;
-            }
-        }
-
-        private void sweep(boolean down) {
-
-            if (down) {
-                downValues();
-            } else {
-                upValues();
-            }
-
-            SortedSet<Region> regions = new TreeSet<Region>(regionComparator);
-            for (Segment s : segments) {
-                s.region = new Region();
-                s.region.minOrderNumber = s.orderNumber;
-                s.region.segments.add(s);
-                s.region.d = s.d;
-                regions.add(s.region);
-            }
-
-            for (Segment s : segments) {
-                for (LayoutNode n : s.nodes) {
-                    if (n.pos != 0) {
-                        LayoutNode prevNode = layers[n.layer].get(n.pos - 1);
-                        if (prevNode.x + prevNode.width + xOffset == n.x) {
-                            Segment other = hashMap.get(prevNode);
-                            Region r1 = s.region;
-                            Region r2 = other.region;
-                            // They are close together
-                            if (r1 != r2 && r2.d >= r1.d) {
-
-                                if (r2.segments.size() < r1.segments.size()) {
-
-                                    r1.d = (r1.d * r1.segments.size() + r2.d * r2.segments.size()) / (r1.segments.size() + r2.segments.size());
-
-                                    for (Segment tempS : r2.segments) {
-                                        r1.segments.add(tempS);
-                                        tempS.region = r1;
-                                        r1.minOrderNumber = Math.min(r1.minOrderNumber, tempS.orderNumber);
-                                    }
-
-                                    regions.remove(r2);
-                                } else {
-
-                                    r2.d = (r1.d * r1.segments.size() + r2.d * r2.segments.size()) / (r1.segments.size() + r2.segments.size());
-
-                                    for (Segment tempS : r1.segments) {
-                                        r2.segments.add(tempS);
-                                        tempS.region = r2;
-                                        r2.minOrderNumber = Math.min(r2.minOrderNumber, tempS.orderNumber);
-                                    }
-
-                                    regions.remove(r1);
-                                }
-                            }
-                        }
-                    }
-                }
-            }
-
-
-
-            ArrayList<Region> reversedRegions = new ArrayList<Region>();
-            for (Region r : regions) {
-                if (r.d < 0) {
-                    processRegion(r, down);
-                } else {
-                    reversedRegions.add(0, r);
-                }
-            }
-
-            for (Region r : reversedRegions) {
-                processRegion(r, down);
-            }
-
-        }
-
-        private void processRegion(Region r, boolean down) {
-
-            // Do not move
-            if ((int) r.d == 0) {
-                return;
-            }
-
-            ArrayList<Segment> arr = new ArrayList<Segment>();
-            for (Segment s : r.segments) {
-                arr.add(s);
-            }
-
-            if (r.d > 0) {
-                Collections.reverse(arr);
-            }
-
-            for (Segment s : arr) {
-
-
-                int min = (int) r.d;
-                if (min < 0) {
-                    min = -min;
-                }
-
-                for (LayoutNode n : s.nodes) {
-
-                    int layer = n.layer;
-                    int pos = n.pos;
-
-
-                    if (r.d > 0) {
-
-                        if (pos != layers[layer].size() - 1) {
-
-                            int off = layers[layer].get(pos + 1).x - n.x - xOffset - n.width;
-                            assert off >= 0;
-                            if (off < min) {
-                                min = off;
-                            }
-                        }
-
-                    } else {
-
-                        if (pos != 0) {
-
-                            int off = n.x - xOffset - layers[layer].get(pos - 1).x - layers[layer].get(pos - 1).width;
-                            assert off >= 0;
-                            if (off < min) {
-                                min = off;
-                            }
-                        }
-                    }
-                }
-
-                assert min >= 0;
-                if (min != 0) {
-                    for (LayoutNode n : s.nodes) {
-                        if (r.d > 0) {
-                            n.x += min;
-                        } else {
-                            n.x -= min;
-                        }
-
-                    }
-                }
-            }
-        }
-
-        protected void run() {
-
-            generateSegments();
-            addEdges();
-            topologicalSorting();
-            initialPositions();
-            for (int i = 0; i < SWEEP_ITERATIONS; i++) {
-
-                sweep(true);
-                sweep(true);
-                sweep(false);
-                sweep(false);
-            }
-
-            sweep(true);
-            sweep(true);
-        }
-    }
     private static Comparator<LayoutNode> crossingNodeComparator = new Comparator<LayoutNode>() {
 
+        @Override
         public int compare(LayoutNode n1, LayoutNode n2) {
             return n1.crossingNumber - n2.crossingNumber;
         }
@@ -1104,22 +819,26 @@
             }
         }
 
-        protected void run() {
-
+        @SuppressWarnings("unchecked")
+        private void createLayers() {
             layers = new List[layerCount];
 
             for (int i = 0; i < layerCount; i++) {
-                layers[i] = new ArrayList<LayoutNode>();
+                layers[i] = new ArrayList<>();
             }
+        }
 
+        @Override
+        protected void run() {
+            createLayers();
 
             // Generate initial ordering
-            HashSet<LayoutNode> visited = new HashSet<LayoutNode>();
+            HashSet<LayoutNode> visited = new HashSet<>();
             for (LayoutNode n : nodes) {
                 if (n.layer == 0) {
                     layers[0].add(n);
                     visited.add(n);
-                } else if (n.preds.size() == 0) {
+                } else if (n.preds.isEmpty()) {
                     layers[n.layer].add(n);
                     visited.add(n);
                 }
@@ -1136,7 +855,6 @@
                 }
             }
 
-
             updatePositions();
 
             initX();
@@ -1146,10 +864,7 @@
                 downSweep();
                 upSweep();
             }
-
-        /*for(int i=0; i<CROSSING_ITERATIONS; i++) {
-        doubleSweep();
-        }*/
+            downSweep();
         }
 
         private void initX() {
@@ -1191,25 +906,23 @@
                 for (LayoutNode n : layers[i]) {
 
                     int sum = 0;
+                    int count = 0;
                     for (LayoutEdge e : n.preds) {
                         int cur = e.from.x + e.relativeFrom;
-
-                        /*pos;
-                        if(e.from.width != 0 && e.relativeFrom != 0) {
-                        cur += (float)e.relativeFrom / (float)(e.from.width);
-                        }*/
-
-                        sum += cur;
+                        int factor = 1;
+                        if (e.vip) {
+                            factor = VIP_BONUS;
+                        }
+                        sum += cur * factor;
+                        count += factor;
                     }
 
-                    if (n.preds.size() > 0) {
-                        sum /= n.preds.size();
+                    if (count > 0) {
+                        sum /= count;
                         n.crossingNumber = sum;
-                    //if(n.vertex == null) n.crossingNumber += layers[i].size();
                     }
                 }
 
-
                 updateCrossingNumbers(i, true);
                 Collections.sort(layers[i], crossingNodeComparator);
                 updateXOfLayer(i);
@@ -1234,9 +947,9 @@
                     next = layers[index].get(i + 1);
                 }
 
-                boolean cond = (n.succs.size() == 0);
+                boolean cond = n.succs.isEmpty();
                 if (down) {
-                    cond = (n.preds.size() == 0);
+                    cond = n.preds.isEmpty();
                 }
 
                 if (cond) {
@@ -1251,44 +964,6 @@
                 }
             }
         }
-        /*
-        private void doubleSweep() {
-        // Downsweep
-        for(int i=0; i<layerCount*2; i++) {
-        int index = i;
-        if(index >= layerCount) {
-        index = 2*layerCount - i - 1;
-        }
-        for(LayoutNode n : layers[index]) {
-        float sum = 0.0f;
-        for(LayoutEdge e : n.preds) {
-        float cur = e.from.pos;
-        if(e.from.width != 0 && e.relativeFrom != 0) {
-        cur += (float)e.relativeFrom / (float)(e.from.width);
-        }
-        sum += cur;
-        }
-        for(LayoutEdge e : n.succs) {
-        float cur = e.to.pos;
-        if(e.to.width != 0 && e.relativeTo != 0) {
-        cur += (float)e.relativeTo / (float)(e.to.width);
-        }
-        sum += cur;
-        }
-        if(n.preds.size() + n.succs.size() > 0) {
-        sum /= n.preds.size() + n.succs.size();
-        n.crossingNumber = sum;
-        }
-        }
-        Collections.sort(layers[index], crossingNodeComparator);
-        updateXOfLayer(index);
-        int z = 0;
-        for(LayoutNode n : layers[index]) {
-        n.pos = z;
-        z++;
-        }
-        }
-        }*/
 
         private void upSweep() {
             // Upsweep
@@ -1300,21 +975,21 @@
 
                 for (LayoutNode n : layers[i]) {
 
+                    int count = 0;
                     int sum = 0;
                     for (LayoutEdge e : n.succs) {
-                        int cur = e.to.x + e.relativeTo;//pos;
-                                                /*
-                        if(e.to.width != 0 && e.relativeTo != 0) {
-                        cur += (float)e.relativeTo / (float)(e.to.width);
-                        }*/
-
-                        sum += cur;
+                        int cur = e.to.x + e.relativeTo;
+                        int factor = 1;
+                        if (e.vip) {
+                            factor = VIP_BONUS;
+                        }
+                        sum += cur * factor;
+                        count += factor;
                     }
 
-                    if (n.succs.size() > 0) {
-                        sum /= n.succs.size();
+                    if (count > 0) {
+                        sum /= count;
                         n.crossingNumber = sum;
-                    //if(n.vertex == null) n.crossingNumber += layers[i].size();
                     }
 
                 }
@@ -1331,15 +1006,10 @@
             }
         }
 
-        private int evaluate() {
-            // TODO: Implement efficient evaluate / crossing min
-            return 0;
-        }
-
         @Override
         public void postCheck() {
 
-            HashSet<LayoutNode> visited = new HashSet<LayoutNode>();
+            HashSet<LayoutNode> visited = new HashSet<>();
             for (int i = 0; i < layers.length; i++) {
                 for (LayoutNode n : layers[i]) {
                     assert !visited.contains(n);
@@ -1353,9 +1023,10 @@
 
     private class AssignYCoordinates extends AlgorithmPart {
 
+        @Override
         protected void run() {
             int curY = 0;
-            //maxLayerHeight = new int[layers.length];
+
             for (int i = 0; i < layers.length; i++) {
                 int maxHeight = 0;
                 int baseLine = 0;
@@ -1383,10 +1054,8 @@
                     }
                 }
 
-                //maxLayerHeight[i] = maxHeight + baseLine + bottomBaseLine;
-
                 curY += maxHeight + baseLine + bottomBaseLine;
-                curY += layerOffset + (int) Math.sqrt(maxXOffset);
+                curY += layerOffset + ((int) (Math.sqrt(maxXOffset) * 1.5));
             }
         }
     }
@@ -1411,26 +1080,27 @@
             }
         }
 
+        @Override
         protected void run() {
             oldNodeCount = nodes.size();
 
-
             if (combine == Combine.SAME_OUTPUTS) {
 
                 Comparator<LayoutEdge> comparator = new Comparator<LayoutEdge>() {
 
+                    @Override
                     public int compare(LayoutEdge e1, LayoutEdge e2) {
                         return e1.to.layer - e2.to.layer;
                     }
                 };
-                HashMap<Integer, List<LayoutEdge>> portHash = new HashMap<Integer, List<LayoutEdge>>();
-                ArrayList<LayoutNode> currentNodes = new ArrayList<LayoutNode>(nodes);
+                HashMap<Integer, List<LayoutEdge>> portHash = new HashMap<>();
+                ArrayList<LayoutNode> currentNodes = new ArrayList<>(nodes);
                 for (LayoutNode n : currentNodes) {
                     portHash.clear();
 
-                    ArrayList<LayoutEdge> succs = new ArrayList<LayoutEdge>(n.succs);
-                    HashMap<Integer, LayoutNode> topNodeHash = new HashMap<Integer, LayoutNode>();
-                    HashMap<Integer, HashMap<Integer, LayoutNode>> bottomNodeHash = new HashMap<Integer, HashMap<Integer, LayoutNode>>();
+                    ArrayList<LayoutEdge> succs = new ArrayList<>(n.succs);
+                    HashMap<Integer, LayoutNode> topNodeHash = new HashMap<>();
+                    HashMap<Integer, HashMap<Integer, LayoutNode>> bottomNodeHash = new HashMap<>();
                     for (LayoutEdge e : succs) {
                         assert e.from.layer < e.to.layer;
                         if (e.from.layer != e.to.layer - 1) {
@@ -1449,6 +1119,7 @@
                                     topEdge.relativeTo = topNode.width / 2;
                                     topEdge.to = topNode;
                                     topEdge.link = e.link;
+                                    topEdge.vip = e.vip;
                                     e.from.succs.add(topEdge);
                                     topNode.preds.add(topEdge);
                                 } else {
@@ -1464,6 +1135,7 @@
                                     topEdge.relativeTo = topNode.width / 2;
                                     topEdge.to = topNode;
                                     topEdge.link = e.link;
+                                    topEdge.vip = e.vip;
                                     e.from.succs.add(topEdge);
                                     topNode.preds.add(topEdge);
                                     topNodeHash.put(e.relativeFrom, topNode);
@@ -1491,6 +1163,7 @@
                                 bottomEdge.relativeFrom = bottomNode.width / 2;
                                 bottomEdge.from = bottomNode;
                                 bottomEdge.link = e.link;
+                                bottomEdge.vip = e.vip;
                                 e.to.preds.add(bottomEdge);
                                 bottomEdgeHash.put(topEdge, bottomEdge);
                                 bottomNode.succs.add(bottomEdge);
@@ -1500,17 +1173,12 @@
                                 if (!portHash.containsKey(i)) {
                                     portHash.put(i, new ArrayList<LayoutEdge>());
                                 }
-
-                                if (n.vertex.toString().equals("1012 CastPP")) {
-                                    int x = 0;
-                                }
-
                                 portHash.get(i).add(e);
                             }
                         }
                     }
 
-                    succs = new ArrayList<LayoutEdge>(n.succs);
+                    succs = new ArrayList<>(n.succs);
                     for (LayoutEdge e : succs) {
 
                         Integer i = e.relativeFrom;
@@ -1528,13 +1196,13 @@
                                     maxLayer = Math.max(maxLayer, curEdge.to.layer);
                                 }
 
-
                                 int cnt = maxLayer - n.layer - 1;
                                 LayoutEdge[] edges = new LayoutEdge[cnt];
                                 LayoutNode[] nodes = new LayoutNode[cnt];
                                 edges[0] = new LayoutEdge();
                                 edges[0].from = n;
                                 edges[0].relativeFrom = i;
+                                edges[0].vip = e.vip;
                                 n.succs.add(edges[0]);
 
                                 nodes[0] = new LayoutNode();
@@ -1546,6 +1214,7 @@
                                 edges[0].relativeTo = nodes[0].width / 2;
                                 for (int j = 1; j < cnt; j++) {
                                     edges[j] = new LayoutEdge();
+                                    edges[j].vip = e.vip;
                                     edges[j].from = nodes[j - 1];
                                     edges[j].relativeFrom = nodes[j - 1].width / 2;
                                     nodes[j - 1].succs.add(edges[j]);
@@ -1577,7 +1246,7 @@
             } else if (combine == Combine.SAME_INPUTS) {
                 throw new UnsupportedOperationException("Currently not supported");
             } else {
-                ArrayList<LayoutNode> currentNodes = new ArrayList<LayoutNode>(nodes);
+                ArrayList<LayoutNode> currentNodes = new ArrayList<>(nodes);
                 for (LayoutNode n : currentNodes) {
                     for (LayoutEdge e : n.succs) {
                         processSingleEdge(e);
@@ -1604,6 +1273,7 @@
             n.preds.add(e);
             nodes.add(n);
             LayoutEdge result = new LayoutEdge();
+            result.vip = e.vip;
             n.succs.add(result);
             result.from = n;
             result.relativeFrom = n.width / 2;
@@ -1623,7 +1293,7 @@
 
         @Override
         public void postCheck() {
-            ArrayList<LayoutNode> currentNodes = new ArrayList<LayoutNode>(nodes);
+            ArrayList<LayoutNode> currentNodes = new ArrayList<>(nodes);
             for (LayoutNode n : currentNodes) {
                 for (LayoutEdge e : n.succs) {
                     assert e.from.layer == e.to.layer - 1;
@@ -1648,91 +1318,114 @@
             }
         }
 
+        @Override
         protected void run() {
-            HashSet<LayoutNode> set = new HashSet<LayoutNode>();
+            assignLayerDownwards();
+            assignLayerUpwards();
+        }
+
+        private void assignLayerDownwards() {
+            ArrayList<LayoutNode> hull = new ArrayList<>();
             for (LayoutNode n : nodes) {
-                if (n.preds.size() == 0) {
-                    set.add(n);
+                if (n.preds.isEmpty()) {
+                    hull.add(n);
                     n.layer = 0;
                 }
             }
 
             int z = minLayerDifference;
-            HashSet<LayoutNode> newSet = new HashSet<LayoutNode>();
-            HashSet<LayoutNode> failed = new HashSet<LayoutNode>();
-            while (!set.isEmpty()) {
-
-                newSet.clear();
-                failed.clear();
-
-                for (LayoutNode n : set) {
-
+            while (!hull.isEmpty()) {
+                ArrayList<LayoutNode> newSet = new ArrayList<>();
+                for (LayoutNode n : hull) {
                     for (LayoutEdge se : n.succs) {
                         LayoutNode s = se.to;
-                        if (!newSet.contains(s) && !failed.contains(s)) {
-                            boolean ok = true;
+                        if (s.layer != -1) {
+                            // This node was assigned before.
+                        } else {
+                            boolean unassignedPred = false;
                             for (LayoutEdge pe : s.preds) {
                                 LayoutNode p = pe.from;
-                                if (p.layer == -1) {
-                                    ok = false;
+                                if (p.layer == -1 || p.layer >= z) {
+                                    // This now has an unscheduled successor or a successor that was scheduled only in this round.
+                                    unassignedPred = true;
                                     break;
                                 }
                             }
 
-                            if (ok) {
+                            if (unassignedPred) {
+                                // This successor node can not yet be assigned.
+                            } else {
+                                s.layer = z;
                                 newSet.add(s);
-                            } else {
-                                failed.add(s);
                             }
                         }
                     }
-
                 }
 
-                for (LayoutNode n : newSet) {
-                    n.layer = z;
-                }
-
-                // Swap sets
-                HashSet<LayoutNode> tmp = set;
-                set = newSet;
-                newSet = tmp;
+                hull = newSet;
                 z += minLayerDifference;
             }
 
-            optimize(set);
+            layerCount = z - minLayerDifference;
+            for (LayoutNode n : nodes) {
+                n.layer = (layerCount - 1 - n.layer);
+            }
+        }
+
+        private void assignLayerUpwards() {
+            ArrayList<LayoutNode> hull = new ArrayList<>();
+            for (LayoutNode n : nodes) {
+                if (n.succs.isEmpty()) {
+                    hull.add(n);
+                } else {
+                    n.layer = -1;
+                }
+            }
+
+            int z = minLayerDifference;
+            while (!hull.isEmpty()) {
+                ArrayList<LayoutNode> newSet = new ArrayList<>();
+                for (LayoutNode n : hull) {
+                    if (n.layer < z) {
+                        for (LayoutEdge se : n.preds) {
+                            LayoutNode s = se.from;
+                            if (s.layer != -1) {
+                                // This node was assigned before.
+                            } else {
+                                boolean unassignedSucc = false;
+                                for (LayoutEdge pe : s.succs) {
+                                    LayoutNode p = pe.to;
+                                    if (p.layer == -1 || p.layer >= z) {
+                                        // This now has an unscheduled successor or a successor that was scheduled only in this round.
+                                        unassignedSucc = true;
+                                        break;
+                                    }
+                                }
+
+                                if (unassignedSucc) {
+                                    // This predecessor node can not yet be assigned.
+                                } else {
+                                    s.layer = z;
+                                    newSet.add(s);
+                                }
+                            }
+                        }
+                    } else {
+                        newSet.add(n);
+                    }
+                }
+
+                hull = newSet;
+                z += minLayerDifference;
+            }
 
             layerCount = z - minLayerDifference;
 
-            for (Vertex v : lastLayerHint) {
-
-                LayoutNode n = vertexToLayoutNode.get(v);
-                assert n.succs.size() == 0;
-                n.layer = layerCount - 1;
-            }
-
-            for (Vertex v : firstLayerHint) {
-                LayoutNode n = vertexToLayoutNode.get(v);
-                assert n.preds.size() == 0;
-                assert n.layer == 0;
+            for (LayoutNode n : nodes) {
+                n.layer = (layerCount - 1 - n.layer);
             }
         }
 
-        public void optimize(HashSet<LayoutNode> set) {
-
-            for (LayoutNode n : set) {
-                if (n.preds.size() == 0 && n.succs.size() > 0) {
-                    int minLayer = n.succs.get(0).to.layer;
-                    for (LayoutEdge e : n.succs) {
-                        minLayer = Math.min(minLayer, e.to.layer);
-                    }
-
-                    n.layer = minLayer - 1;
-                }
-            }
-
-        }
-
         @Override
         public void postCheck() {
             for (LayoutNode n : nodes) {
@@ -1750,11 +1443,12 @@
         private HashSet<LayoutNode> visited;
         private HashSet<LayoutNode> active;
 
+        @Override
         protected void run() {
 
-            // Remove self-edges, TODO: Special treatment
+            // Remove self-edges
             for (LayoutNode node : nodes) {
-                ArrayList<LayoutEdge> succs = new ArrayList<LayoutEdge>(node.succs);
+                ArrayList<LayoutEdge> succs = new ArrayList<>(node.succs);
                 for (LayoutEdge e : succs) {
                     assert e.from == node;
                     if (e.to == node) {
@@ -1780,18 +1474,16 @@
                 }
             }
 
-
             // Start DFS and reverse back edges
-            visited = new HashSet<LayoutNode>();
-            active = new HashSet<LayoutNode>();
+            visited = new HashSet<>();
+            active = new HashSet<>();
             for (LayoutNode node : nodes) {
                 DFS(node);
             }
 
-
             for (LayoutNode node : nodes) {
 
-                SortedSet<Integer> reversedDown = new TreeSet<Integer>();
+                SortedSet<Integer> reversedDown = new TreeSet<>();
 
                 for (LayoutEdge e : node.succs) {
                     if (reversedLinks.contains(e.link)) {
@@ -1799,12 +1491,11 @@
                     }
                 }
 
-
                 SortedSet<Integer> reversedUp = null;
                 if (reversedDown.size() == 0) {
-                    reversedUp = new TreeSet<Integer>(Collections.reverseOrder());
+                    reversedUp = new TreeSet<>(Collections.reverseOrder());
                 } else {
-                    reversedUp = new TreeSet<Integer>();
+                    reversedUp = new TreeSet<>();
                 }
 
                 for (LayoutEdge e : node.preds) {
@@ -1818,7 +1509,7 @@
                 int curX = 0;
                 int curWidth = node.width + reversedDown.size() * offset;
                 for (int pos : reversedDown) {
-                    ArrayList<LayoutEdge> reversedSuccs = new ArrayList<LayoutEdge>();
+                    ArrayList<LayoutEdge> reversedSuccs = new ArrayList<>();
                     for (LayoutEdge e : node.succs) {
                         if (e.relativeFrom == pos && reversedLinks.contains(e.link)) {
                             reversedSuccs.add(e);
@@ -1826,7 +1517,7 @@
                         }
                     }
 
-                    ArrayList<Point> startPoints = new ArrayList<Point>();
+                    ArrayList<Point> startPoints = new ArrayList<>();
                     startPoints.add(new Point(curWidth, curX));
                     startPoints.add(new Point(pos, curX));
                     startPoints.add(new Point(pos, reversedDown.size() * offset));
@@ -1856,7 +1547,7 @@
 
                 int oldNodeHeight = node.height;
                 for (int pos : reversedUp) {
-                    ArrayList<LayoutEdge> reversedPreds = new ArrayList<LayoutEdge>();
+                    ArrayList<LayoutEdge> reversedPreds = new ArrayList<>();
                     for (LayoutEdge e : node.preds) {
                         if (e.relativeTo == pos && reversedLinks.contains(e.link)) {
                             if (reversedDown.size() == 0) {
@@ -1869,7 +1560,7 @@
                         }
                     }
                     node.height += offset;
-                    ArrayList<Point> endPoints = new ArrayList<Point>();
+                    ArrayList<Point> endPoints = new ArrayList<>();
 
                     if (reversedDown.size() == 0) {
 
@@ -1887,7 +1578,6 @@
                     curX += offset;
                     node.bottomYOffset += offset;
 
-
                     endPoints.add(new Point(pos, node.height));
                     endPoints.add(new Point(pos, oldNodeHeight));
                     for (LayoutEdge e : reversedPreds) {
@@ -1895,7 +1585,6 @@
                     }
                 }
 
-
                 if (minX < 0) {
                     for (LayoutEdge e : node.preds) {
                         e.relativeTo -= minX;
@@ -1917,7 +1606,7 @@
                 return;
             }
 
-            Stack<LayoutNode> stack = new Stack<LayoutNode>();
+            Stack<LayoutNode> stack = new Stack<>();
             stack.push(startNode);
 
             while (!stack.empty()) {
@@ -1934,7 +1623,7 @@
                 visited.add(node);
                 active.add(node);
 
-                ArrayList<LayoutEdge> succs = new ArrayList<LayoutEdge>(node.succs);
+                ArrayList<LayoutEdge> succs = new ArrayList<>(node.succs);
                 for (LayoutEdge e : succs) {
                     if (active.contains(e.to)) {
                         assert visited.contains(e.to);
@@ -1989,8 +1678,8 @@
 
             for (LayoutNode n : nodes) {
 
-                HashSet<LayoutNode> curVisited = new HashSet<LayoutNode>();
-                Queue<LayoutNode> queue = new LinkedList<LayoutNode>();
+                HashSet<LayoutNode> curVisited = new HashSet<>();
+                Queue<LayoutNode> queue = new LinkedList<>();
                 for (LayoutEdge e : n.succs) {
                     LayoutNode s = e.to;
                     queue.add(s);
@@ -2013,7 +1702,15 @@
     }
     private Comparator<Link> linkComparator = new Comparator<Link>() {
 
+        @Override
         public int compare(Link l1, Link l2) {
+            if (l1.isVIP() && !l2.isVIP()) {
+                return -1;
+            }
+
+            if (!l1.isVIP() && l2.isVIP()) {
+                return 1;
+            }
 
             int result = l1.getFrom().getVertex().compareTo(l2.getFrom().getVertex());
             if (result != 0) {
@@ -2034,9 +1731,10 @@
 
     private class BuildDatastructure extends AlgorithmPart {
 
+        @Override
         protected void run() {
             // Set up nodes
-            List<Vertex> vertices = new ArrayList<Vertex>(graph.getVertices());
+            List<Vertex> vertices = new ArrayList<>(graph.getVertices());
             Collections.sort(vertices);
 
             for (Vertex v : vertices) {
@@ -2050,7 +1748,7 @@
             }
 
             // Set up edges
-            List<Link> links = new ArrayList<Link>(graph.getLinks());
+            List<Link> links = new ArrayList<>(graph.getLinks());
             Collections.sort(links, linkComparator);
             for (Link l : links) {
                 LayoutEdge edge = new LayoutEdge();
@@ -2061,14 +1759,15 @@
                 edge.relativeFrom = l.getFrom().getRelativePosition().x;
                 edge.relativeTo = l.getTo().getRelativePosition().x;
                 edge.link = l;
+                edge.vip = l.isVIP();
                 edge.from.succs.add(edge);
                 edge.to.preds.add(edge);
-            //assert edge.from != edge.to; // No self-loops allowed
+                //assert edge.from != edge.to; // No self-loops allowed
             }
 
             for (Link l : importantLinks) {
-                if (!vertexToLayoutNode.containsKey(l.getFrom().getVertex()) ||
-                        vertexToLayoutNode.containsKey(l.getTo().getVertex())) {
+                if (!vertexToLayoutNode.containsKey(l.getFrom().getVertex())
+                        || vertexToLayoutNode.containsKey(l.getTo().getVertex())) {
                     continue;
                 }
                 LayoutNode from = vertexToLayoutNode.get(l.getFrom().getVertex());
@@ -2104,7 +1803,8 @@
         }
     }
 
+    @Override
     public void doRouting(LayoutGraph graph) {
-    // Do nothing for now
+        // Do nothing for now
     }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/InterClusterConnection.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/InterClusterConnection.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -73,4 +73,8 @@
     public String toString() {
         return "InterClusterConnection[from=" + getFrom() + ", to=" + getTo() + "]";
     }
+
+    public boolean isVIP() {
+        return false;
+    }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/Node.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/Node.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -90,8 +90,8 @@
     protected Node(Graph<N, E> graph, N data) {
         setData(data);
         this.graph = graph;
-        inEdges = new ArrayList<Edge<N, E>>();
-        outEdges = new ArrayList<Edge<N, E>>();
+        inEdges = new ArrayList<>();
+        outEdges = new ArrayList<>();
     }
 
     protected void addInEdge(Edge<N, E> e) {
@@ -125,7 +125,7 @@
     }
 
     public List<Node<N, E>> getSuccessors() {
-        ArrayList<Node<N, E>> succ = new ArrayList<Node<N, E>>();
+        ArrayList<Node<N, E>> succ = new ArrayList<>();
         for (Edge<N, E> e : getOutEdges()) {
             Node<N, E> n = e.getDest();
             if (!succ.contains(n)) {
@@ -136,7 +136,7 @@
     }
 
     public List<Node<N, E>> getPredecessors() {
-        ArrayList<Node<N, E>> pred = new ArrayList<Node<N, E>>();
+        ArrayList<Node<N, E>> pred = new ArrayList<>();
         for (Edge<N, E> e : getInEdges()) {
             Node<N, E> n = e.getSource();
             if (!pred.contains(n)) {
--- a/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/OldHierarchicalLayoutManager.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,1222 +0,0 @@
-/*
- * Copyright (c) 2008, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- *
- */
-package com.sun.hotspot.igv.hierarchicallayout;
-
-import java.awt.Point;
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.Comparator;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-import com.sun.hotspot.igv.layout.LayoutGraph;
-import com.sun.hotspot.igv.layout.LayoutManager;
-import com.sun.hotspot.igv.layout.Link;
-import com.sun.hotspot.igv.layout.Port;
-import com.sun.hotspot.igv.layout.Vertex;
-
-/**
- *
- * @author Thomas Wuerthinger
- */
-public class OldHierarchicalLayoutManager implements LayoutManager {
-
-    public static final int DUMMY_WIDTH = 0;
-    public static final int DUMMY_HEIGHT = 0;
-    public static final int LAYER_OFFSET = 50;
-    public static final int OFFSET = 8;
-    public static final boolean VERTICAL_LAYOUT = true;
-    public static final boolean ASSERT = false;
-    public static final boolean TRACE = false;
-    public static final Timing initTiming = new Timing("init");
-    public static final Timing removeCyclesTiming = new Timing("removeCycles");
-    public static final Timing reversedEdgesTiming = new Timing("reversedEdges");
-    public static final Timing assignLayersTiming = new Timing("assignLayers");
-    public static final Timing dummyNodesTiming = new Timing("dummyNodes");
-    public static final Timing crossingReductionTiming = new Timing("crossingReduction");
-    public static final Timing assignCoordinatesTiming = new Timing("assignCoordinates");
-    public static final Timing assignRealTiming = new Timing("assignReal");
-    public static final Timing rootVertexTiming = new Timing("rootVertex");
-    public static final Timing createEdgesTiming = new Timing("createEdges");
-    public static final Timing optimizeMedianTiming = new Timing("optimizeMedian");
-    private Combine combine;
-
-    public enum Combine {
-
-        NONE,
-        SAME_INPUTS,
-        SAME_OUTPUTS
-    }
-
-    private class NodeData {
-
-        private Map<Port, Integer> reversePositions;
-        private Vertex node;
-        private Link edge;
-        private int layer;
-        private int x;
-        private int y;
-        private int width;
-
-        public NodeData(Vertex node) {
-            reversePositions = new HashMap<Port, Integer>();
-            layer = -1;
-            this.node = node;
-            assert node != null;
-
-            if (VERTICAL_LAYOUT) {
-                width = node.getSize().width;
-            } else {
-                width = node.getSize().height;
-            }
-        }
-
-        public NodeData(Link edge) {
-            layer = -1;
-            this.edge = edge;
-            assert edge != null;
-
-            if (VERTICAL_LAYOUT) {
-                width = DUMMY_WIDTH;
-            } else {
-                width = DUMMY_HEIGHT;
-            }
-        }
-
-        public Vertex getNode() {
-            return node;
-        }
-
-        public Link getEdge() {
-            return edge;
-        }
-
-        public int getCoordinate() {
-            return x;
-        }
-
-        public void setCoordinate(int x) {
-            this.x = x;
-        }
-
-        public int getX() {
-            if (VERTICAL_LAYOUT) {
-                return x;
-            } else {
-                return y;
-            }
-        }
-
-        public int getY() {
-            if (VERTICAL_LAYOUT) {
-                return y;
-            } else {
-                return x;
-            }
-        }
-
-        public void setLayerCoordinate(int y) {
-            this.y = y;
-        }
-
-        public void setLayer(int x) {
-            layer = x;
-        }
-
-        public int getLayer() {
-            return layer;
-        }
-
-        public boolean isDummy() {
-            return edge != null;
-        }
-
-        public int getWidth() {
-            return width;
-        }
-
-        public void addReversedStartEdge(Edge<NodeData, EdgeData> e) {
-            assert e.getData().isReversed();
-            Port port = e.getData().getEdge().getTo();
-            int pos = addReversedPort(port);
-            Point start = e.getData().getRelativeStart();
-            e.getData().addStartPoint(start);
-            int yCoord = node.getSize().height + width - node.getSize().width;
-            e.getData().addStartPoint(new Point(start.x, yCoord));
-            e.getData().addStartPoint(new Point(pos, yCoord));
-            e.getData().setRelativeStart(new Point(pos, 0));
-        }
-
-        private int addReversedPort(Port p) {
-            if (reversePositions.containsKey(p)) {
-                return reversePositions.get(p);
-            } else {
-                width += OFFSET;
-                reversePositions.put(p, width);
-                return width;
-            }
-        }
-
-        public void addReversedEndEdge(Edge<NodeData, EdgeData> e) {
-            assert e.getData().isReversed();
-            int pos = addReversedPort(e.getData().getEdge().getFrom());
-            Point end = e.getData().getRelativeEnd();
-            e.getData().setRelativeEnd(new Point(pos, node.getSize().height));
-            int yCoord = 0 - width + node.getSize().width;
-            e.getData().addEndPoint(new Point(pos, yCoord));
-            e.getData().addEndPoint(new Point(end.x, yCoord));
-            e.getData().addEndPoint(end);
-        }
-
-        public int getHeight() {
-            if (isDummy()) {
-                if (VERTICAL_LAYOUT) {
-                    return DUMMY_HEIGHT;
-                } else {
-                    return DUMMY_WIDTH;
-                }
-
-            } else {
-                if (VERTICAL_LAYOUT) {
-                    return node.getSize().height;
-                } else {
-                    return node.getSize().width;
-                }
-            }
-        }
-
-        @Override
-        public String toString() {
-            if (isDummy()) {
-                return edge.toString() + "(layer=" + layer + ")";
-            } else {
-                return node.toString() + "(layer=" + layer + ")";
-            }
-        }
-    }
-
-    private class EdgeData {
-
-        private Point relativeEnd;
-        private Point relativeStart;
-        private List<Point> startPoints;
-        private List<Point> endPoints;
-        private boolean important;
-        private boolean reversed;
-        private Link edge;
-
-        public EdgeData(Link edge) {
-            this(edge, false);
-        }
-
-        public EdgeData(Link edge, boolean rev) {
-            this.edge = edge;
-            reversed = rev;
-            relativeStart = edge.getFrom().getRelativePosition();
-            relativeEnd = edge.getTo().getRelativePosition();
-            assert relativeStart.x >= 0 && relativeStart.x <= edge.getFrom().getVertex().getSize().width;
-            assert relativeStart.y >= 0 && relativeStart.y <= edge.getFrom().getVertex().getSize().height;
-            assert relativeEnd.x >= 0 && relativeEnd.x <= edge.getTo().getVertex().getSize().width;
-            assert relativeEnd.y >= 0 && relativeEnd.y <= edge.getTo().getVertex().getSize().height;
-            startPoints = new ArrayList<Point>();
-            endPoints = new ArrayList<Point>();
-            this.important = true;
-        }
-
-        public boolean isImportant() {
-            return important;
-        }
-
-        public void setImportant(boolean b) {
-            this.important = b;
-        }
-
-        public List<Point> getStartPoints() {
-            return startPoints;
-        }
-
-        public List<Point> getEndPoints() {
-            return endPoints;
-        }
-
-        public List<Point> getAbsoluteEndPoints() {
-            if (endPoints.size() == 0) {
-                return endPoints;
-            }
-
-            List<Point> result = new ArrayList<Point>();
-            Point point = edge.getTo().getVertex().getPosition();
-            for (Point p : endPoints) {
-                Point p2 = new Point(p.x + point.x, p.y + point.y);
-                result.add(p2);
-            }
-
-            return result;
-        }
-
-        public List<Point> getAbsoluteStartPoints() {
-            if (startPoints.size() == 0) {
-                return startPoints;
-            }
-
-            List<Point> result = new ArrayList<Point>();
-            Point point = edge.getFrom().getVertex().getPosition();
-            for (Point p : startPoints) {
-                Point p2 = new Point(p.x + point.x, p.y + point.y);
-                result.add(p2);
-            }
-
-            return result;
-        }
-
-        public void addEndPoint(Point p) {
-            endPoints.add(p);
-        }
-
-        public void addStartPoint(Point p) {
-            startPoints.add(p);
-        }
-
-        public Link getEdge() {
-            return edge;
-        }
-
-        public void setRelativeEnd(Point p) {
-            relativeEnd = p;
-        }
-
-        public void setRelativeStart(Point p) {
-            relativeStart = p;
-        }
-
-        public Point getRelativeEnd() {
-            return relativeEnd;
-        }
-
-        public Point getRelativeStart() {
-            return relativeStart;
-        }
-
-        public boolean isReversed() {
-            return reversed;
-        }
-
-        public void setReversed(boolean b) {
-            reversed = b;
-        }
-
-        @Override
-        public String toString() {
-            return "EdgeData[reversed=" + reversed + "]";
-        }
-    }
-    private Graph<NodeData, EdgeData> graph;
-    private Map<Vertex, Node<NodeData, EdgeData>> nodeMap;
-    private int layerOffset;
-
-    /** Creates a new instance of HierarchicalPositionManager */
-    public OldHierarchicalLayoutManager(Combine combine) {
-        this(combine, LAYER_OFFSET);
-    }
-
-    public OldHierarchicalLayoutManager(Combine combine, int layerOffset) {
-        this.combine = combine;
-        this.layerOffset = layerOffset;
-    }
-
-    public void doRouting(LayoutGraph graph) {
-    }
-
-    //public void setPositions(PositionedNode rootNode, List<? extends PositionedNode> nodes, List<? extends PositionedEdge> edges) {
-    public void doLayout(LayoutGraph layoutGraph) {
-        doLayout(layoutGraph, new HashSet<Vertex>(), new HashSet<Vertex>());
-    }
-
-    public void doLayout(LayoutGraph layoutGraph, Set<? extends Vertex> firstLayerHint, Set<? extends Vertex> lastLayerHint) {
-        doLayout(layoutGraph, firstLayerHint, lastLayerHint, new HashSet<Link>());
-    }
-
-    public void doLayout(LayoutGraph layoutGraph, Set<? extends Vertex> firstLayerHint, Set<? extends Vertex> lastLayerHint, Set<? extends Link> importantLinksHint) {
-
-        if (TRACE) {
-            System.out.println("HierarchicalPositionManager.doLayout called");
-            System.out.println("Vertex count = " + layoutGraph.getVertices().size() + " Link count = " + layoutGraph.getLinks().size());
-        }
-
-        // Nothing to do => quit immediately
-        if (layoutGraph.getVertices().size() == 0) {
-            return;
-        }
-
-        initTiming.start();
-
-        // Mapping vertex to Node in graph
-        nodeMap = new HashMap<Vertex, Node<NodeData, EdgeData>>();
-
-        graph = new Graph<NodeData, EdgeData>();
-
-        Set<Node<NodeData, EdgeData>> rootNodes = new HashSet<Node<NodeData, EdgeData>>();
-        Set<Vertex> startRootVertices = new HashSet<Vertex>();
-
-        for (Vertex v : layoutGraph.getVertices()) {
-            if (v.isRoot()) {
-                startRootVertices.add(v);
-            }
-        }
-
-        rootVertexTiming.start();
-        Set<Vertex> rootVertices = layoutGraph.findRootVertices(startRootVertices);
-        rootVertexTiming.stop();
-
-
-        for (Vertex node : layoutGraph.getVertices()) {
-
-            NodeData data = new NodeData(node);
-            Node<NodeData, EdgeData> n = graph.createNode(data, node);
-            nodeMap.put(node, n);
-
-            if (rootVertices.contains(node)) {
-                rootNodes.add(n);
-            }
-        }
-
-        Set<? extends Link> links = layoutGraph.getLinks();
-        Link[] linkArr = new Link[links.size()];
-        links.toArray(linkArr);
-
-        List<Link> linkList = new ArrayList<Link>();
-        for (Link l : linkArr) {
-            linkList.add(l);
-        }
-
-        createEdgesTiming.start();
-        Collections.sort(linkList, new Comparator<Link>() {
-
-            public int compare(Link o1, Link o2) {
-                int result = o1.getFrom().getVertex().compareTo(o2.getFrom().getVertex());
-                if (result == 0) {
-                    return o1.getTo().getVertex().compareTo(o2.getTo().getVertex());
-                } else {
-                    return result;
-                }
-            }
-        });
-
-        for (Link edge : linkList) {
-            EdgeData data = new EdgeData(edge);
-            graph.createEdge(graph.getNode(edge.getFrom().getVertex()), graph.getNode(edge.getTo().getVertex()), data, data);
-            if (importantLinksHint.size() > 0 && !importantLinksHint.contains(edge)) {
-                data.setImportant(false);
-            }
-        }
-        createEdgesTiming.stop();
-
-        initTiming.stop();
-
-        removeCyclesTiming.start();
-
-        // STEP 1: Remove cycles!
-        removeCycles(rootNodes);
-        if (ASSERT) {
-            assert checkRemoveCycles();
-        }
-
-        removeCyclesTiming.stop();
-
-        reversedEdgesTiming.start();
-
-        for (Node<NodeData, EdgeData> n : graph.getNodes()) {
-            List<Edge<NodeData, EdgeData>> edges = new ArrayList<Edge<NodeData, EdgeData>>(n.getOutEdges());
-            Collections.sort(edges, new Comparator<Edge<NodeData, EdgeData>>() {
-
-                public int compare(Edge<NodeData, EdgeData> o1, Edge<NodeData, EdgeData> o2) {
-                    return o2.getData().getRelativeEnd().x - o1.getData().getRelativeEnd().x;
-                }
-            });
-
-
-            for (Edge<NodeData, EdgeData> e : edges) {
-
-                if (e.getData().isReversed()) {
-                    e.getSource().getData().addReversedEndEdge(e);
-                }
-            }
-        }
-
-        for (Node<NodeData, EdgeData> n : graph.getNodes()) {
-            List<Edge<NodeData, EdgeData>> edges = new ArrayList<Edge<NodeData, EdgeData>>(n.getInEdges());
-            Collections.sort(edges, new Comparator<Edge<NodeData, EdgeData>>() {
-
-                public int compare(Edge<NodeData, EdgeData> o1, Edge<NodeData, EdgeData> o2) {
-                    return o2.getData().getRelativeStart().x - o1.getData().getRelativeStart().x;
-                }
-            });
-
-
-            for (Edge<NodeData, EdgeData> e : edges) {
-                if (e.getData().isReversed()) {
-                    e.getDest().getData().addReversedStartEdge(e);
-                }
-            }
-        }
-
-        reversedEdgesTiming.stop();
-
-        assignLayersTiming.start();
-        // STEP 2: Assign layers!
-        int maxLayer = assignLayers(rootNodes, firstLayerHint, lastLayerHint);
-        if (ASSERT) {
-            assert checkAssignLayers();
-        }
-
-        // Put into layer array
-        //int maxLayer = 0;
-        //for(Node<NodeData, EdgeData> n : graph.getNodes()) {
-        //    maxLayer = Math.max(maxLayer, n.getData().getLayer());
-        //}
-
-
-        ArrayList<Node<NodeData, EdgeData>> layers[] = new ArrayList[maxLayer + 1];
-        int layerSizes[] = new int[maxLayer + 1];
-        for (int i = 0; i < maxLayer + 1; i++) {
-            layers[i] = new ArrayList<Node<NodeData, EdgeData>>();
-        }
-
-        for (Node<NodeData, EdgeData> n : graph.getNodes()) {
-            int curLayer = n.getData().getLayer();
-            layers[curLayer].add(n);
-        }
-
-        assignLayersTiming.stop();
-
-        // STEP 3: Insert dummy nodes!
-        dummyNodesTiming.start();
-        insertDummyNodes(layers);
-        if (ASSERT) {
-            assert checkDummyNodes();
-        }
-        dummyNodesTiming.stop();
-
-        crossingReductionTiming.start();
-        // STEP 4: Assign Y coordinates
-        assignLayerCoordinates(layers, layerSizes);
-
-        // STEP 5: Crossing reduction
-        crossingReduction(layers);
-        crossingReductionTiming.stop();
-
-        // STEP 6: Assign Y coordinates
-        assignCoordinatesTiming.start();
-        assignCoordinates(layers);
-        assignCoordinatesTiming.stop();
-
-        assignRealTiming.start();
-
-        // Assign coordinates of nodes to real objects
-        for (Node<NodeData, EdgeData> n : graph.getNodes()) {
-            if (!n.getData().isDummy()) {
-
-                Vertex node = n.getData().getNode();
-                node.setPosition(new Point(n.getData().getX(), n.getData().getY()));
-            }
-        }
-
-        for (Node<NodeData, EdgeData> n : graph.getNodes()) {
-            if (!n.getData().isDummy()) {
-
-                Vertex node = n.getData().getNode();
-
-                List<Edge<NodeData, EdgeData>> outEdges = n.getOutEdges();
-                for (Edge<NodeData, EdgeData> e : outEdges) {
-                    Node<NodeData, EdgeData> succ = e.getDest();
-                    if (succ.getData().isDummy()) {
-                        //PositionedEdge edge = succ.getData().getEdge();
-                        List<Point> points = new ArrayList<Point>();
-                        assignToRealObjects(layerSizes, succ, points);
-                    } else {
-                        List<Point> points = new ArrayList<Point>();
-
-                        EdgeData otherEdgeData = e.getData();
-                        points.addAll(otherEdgeData.getAbsoluteStartPoints());
-                        Link otherEdge = otherEdgeData.getEdge();
-                        Point relFrom = new Point(otherEdgeData.getRelativeStart());
-                        Point from = otherEdge.getFrom().getVertex().getPosition();
-                        relFrom.move(relFrom.x + from.x, relFrom.y + from.y);
-                        points.add(relFrom);
-
-                        Point relTo = new Point(otherEdgeData.getRelativeEnd());
-                        Point to = otherEdge.getTo().getVertex().getPosition();
-                        relTo.move(relTo.x + to.x, relTo.y + to.y);
-                        assert from != null;
-                        assert to != null;
-                        points.add(relTo);
-                        points.addAll(otherEdgeData.getAbsoluteEndPoints());
-                        e.getData().getEdge().setControlPoints(points);
-                    }
-                }
-            }
-        }
-
-        assignRealTiming.stop();
-
-        initTiming.print();
-        removeCyclesTiming.print();
-        reversedEdgesTiming.print();
-        assignLayersTiming.print();
-        dummyNodesTiming.print();
-        crossingReductionTiming.print();
-        assignCoordinatesTiming.print();
-        assignRealTiming.print();
-        rootVertexTiming.print();
-        createEdgesTiming.print();
-        optimizeMedianTiming.print();
-    }
-
-    public boolean onOneLine(Point p1, Point p2, Point p3) {
-        int xoff1 = p1.x - p2.x;
-        int yoff1 = p1.y - p2.y;
-        int xoff2 = p3.x - p2.x;
-        int yoff2 = p3.y - p2.x;
-
-        return (xoff1 * yoff2 - yoff1 * xoff2 == 0);
-    }
-
-    private void assignToRealObjects(int layerSizes[], Node<NodeData, EdgeData> cur, List<Point> points) {
-        assert cur.getData().isDummy();
-
-        ArrayList<Point> otherPoints = new ArrayList<Point>(points);
-
-        int size = layerSizes[cur.getData().getLayer()];
-        otherPoints.add(new Point(cur.getData().getX(), cur.getData().getY() - size / 2));
-        if (otherPoints.size() >= 3 && onOneLine(otherPoints.get(otherPoints.size() - 1), otherPoints.get(otherPoints.size() - 2), otherPoints.get(otherPoints.size() - 3))) {
-            otherPoints.remove(otherPoints.size() - 2);
-        }
-        otherPoints.add(new Point(cur.getData().getX(), cur.getData().getY() + size / 2));
-        if (otherPoints.size() >= 3 && onOneLine(otherPoints.get(otherPoints.size() - 1), otherPoints.get(otherPoints.size() - 2), otherPoints.get(otherPoints.size() - 3))) {
-            otherPoints.remove(otherPoints.size() - 2);
-        }
-
-        for (int i = 0; i < cur.getOutEdges().size(); i++) {
-            Node<NodeData, EdgeData> otherSucc = cur.getOutEdges().get(i).getDest();
-
-            if (otherSucc.getData().isDummy()) {
-                assignToRealObjects(layerSizes, otherSucc, otherPoints);
-            } else {
-                EdgeData otherEdgeData = cur.getOutEdges().get(i).getData();
-                Link otherEdge = otherEdgeData.getEdge();
-
-                List<Point> middlePoints = new ArrayList<Point>(otherPoints);
-                if (cur.getOutEdges().get(i).getData().isReversed()) {
-                    Collections.reverse(middlePoints);
-                }
-
-                ArrayList<Point> copy = new ArrayList<Point>();
-                Point relFrom = new Point(otherEdgeData.getRelativeStart());
-                Point from = otherEdge.getFrom().getVertex().getPosition();
-                //int moveUp = (size - otherEdge.getFrom().getVertex().getSize().height) / 2;
-                relFrom.move(relFrom.x + from.x, relFrom.y + from.y);
-                copy.addAll(otherEdgeData.getAbsoluteStartPoints());
-                copy.add(relFrom);
-                copy.addAll(middlePoints);
-
-                Point relTo = new Point(otherEdgeData.getRelativeEnd());
-                Point to = otherEdge.getTo().getVertex().getPosition();
-                relTo.move(relTo.x + to.x, relTo.y + to.y);
-                copy.add(relTo);
-
-                copy.addAll(otherEdgeData.getAbsoluteEndPoints());
-
-
-                otherEdge.setControlPoints(copy);
-            }
-        }
-    }
-
-    private boolean checkDummyNodes() {
-        for (Edge<NodeData, EdgeData> e : graph.getEdges()) {
-            if (e.getSource().getData().getLayer() != e.getDest().getData().getLayer() - 1) {
-                return false;
-            }
-        }
-
-        return true;
-    }
-
-    private void insertDummyNodes(ArrayList<Node<NodeData, EdgeData>> layers[]) {
-
-        int sum = 0;
-        List<Node<NodeData, EdgeData>> nodes = new ArrayList<Node<NodeData, EdgeData>>(graph.getNodes());
-        int edgeCount = 0;
-        int innerMostLoop = 0;
-
-        for (Node<NodeData, EdgeData> n : nodes) {
-            List<Edge<NodeData, EdgeData>> edges = new ArrayList<Edge<NodeData, EdgeData>>(n.getOutEdges());
-            for (Edge<NodeData, EdgeData> e : edges) {
-
-                edgeCount++;
-                Link edge = e.getData().getEdge();
-                Node<NodeData, EdgeData> destNode = e.getDest();
-                Node<NodeData, EdgeData> lastNode = n;
-                Edge<NodeData, EdgeData> lastEdge = e;
-
-                boolean searchForNode = (combine != Combine.NONE);
-                for (int i = n.getData().getLayer() + 1; i < destNode.getData().getLayer(); i++) {
-
-                    Node<NodeData, EdgeData> foundNode = null;
-                    if (searchForNode) {
-                        for (Node<NodeData, EdgeData> sameLayerNode : layers[i]) {
-                            innerMostLoop++;
-
-                            if (combine == Combine.SAME_OUTPUTS) {
-                                if (sameLayerNode.getData().isDummy() && sameLayerNode.getData().getEdge().getFrom() == edge.getFrom()) {
-                                    foundNode = sameLayerNode;
-                                    break;
-                                }
-                            } else if (combine == Combine.SAME_INPUTS) {
-                                if (sameLayerNode.getData().isDummy() && sameLayerNode.getData().getEdge().getTo() == edge.getTo()) {
-                                    foundNode = sameLayerNode;
-                                    break;
-                                }
-                            }
-                        }
-                    }
-
-                    if (foundNode == null) {
-                        searchForNode = false;
-                        NodeData intermediateData = new NodeData(edge);
-                        Node<NodeData, EdgeData> curNode = graph.createNode(intermediateData, null);
-                        curNode.getData().setLayer(i);
-                        layers[i].add(0, curNode);
-                        sum++;
-                        lastEdge.remove();
-                        graph.createEdge(lastNode, curNode, e.getData(), null);
-                        assert lastNode.getData().getLayer() == curNode.getData().getLayer() - 1;
-                        lastEdge = graph.createEdge(curNode, destNode, e.getData(), null);
-                        lastNode = curNode;
-                    } else {
-                        lastEdge.remove();
-                        lastEdge = graph.createEdge(foundNode, destNode, e.getData(), null);
-                        lastNode = foundNode;
-                    }
-
-                }
-            }
-        }
-
-        if (TRACE) {
-            System.out.println("Number of edges: " + edgeCount);
-        }
-        if (TRACE) {
-            System.out.println("Dummy nodes inserted: " + sum);
-        }
-    }
-
-    private void assignLayerCoordinates(ArrayList<Node<NodeData, EdgeData>> layers[], int layerSizes[]) {
-        int cur = 0;
-        for (int i = 0; i < layers.length; i++) {
-            int maxHeight = 0;
-            for (Node<NodeData, EdgeData> n : layers[i]) {
-                maxHeight = Math.max(maxHeight, n.getData().getHeight());
-            }
-
-            layerSizes[i] = maxHeight;
-            for (Node<NodeData, EdgeData> n : layers[i]) {
-                int curCoordinate = cur + (maxHeight - n.getData().getHeight()) / 2;
-                n.getData().setLayerCoordinate(curCoordinate);
-            }
-            cur += maxHeight + layerOffset;
-
-        }
-    }
-
-    private void assignCoordinates(ArrayList<Node<NodeData, EdgeData>> layers[]) {
-
-        // TODO: change this
-        for (int i = 0; i < layers.length; i++) {
-            ArrayList<Node<NodeData, EdgeData>> curArray = layers[i];
-            int curY = 0;
-            for (Node<NodeData, EdgeData> n : curArray) {
-
-                n.getData().setCoordinate(curY);
-                if (!n.getData().isDummy()) {
-                    curY += n.getData().getWidth();
-                }
-                curY += OFFSET;
-
-            }
-        }
-
-        int curSol = evaluateSolution();
-        if (TRACE) {
-            System.out.println("First coordinate solution found: " + curSol);
-        }
-
-        // Sort to correct order
-        for (int i = 0; i < layers.length; i++) {
-            Collections.sort(layers[i], new Comparator<Node<NodeData, EdgeData>>() {
-
-                public int compare(Node<NodeData, EdgeData> o1, Node<NodeData, EdgeData> o2) {
-                    if (o2.getData().isDummy()) {
-                        return 1;
-                    } else if (o1.getData().isDummy()) {
-                        return -1;
-                    }
-                    return o2.getInEdges().size() + o2.getOutEdges().size() - o1.getInEdges().size() - o1.getOutEdges().size();
-                }
-            });
-        }
-
-
-        optimizeMedianTiming.start();
-        for (int i = 0; i < 2; i++) {
-            optimizeMedian(layers);
-            curSol = evaluateSolution();
-            if (TRACE) {
-                System.out.println("Current coordinate solution found: " + curSol);
-            }
-        }
-        optimizeMedianTiming.stop();
-        normalizeCoordinate();
-
-    }
-
-    private void normalizeCoordinate() {
-
-        int min = Integer.MAX_VALUE;
-        for (Node<NodeData, EdgeData> n : graph.getNodes()) {
-            min = Math.min(min, n.getData().getCoordinate());
-        }
-
-        for (Node<NodeData, EdgeData> n : graph.getNodes()) {
-            n.getData().setCoordinate(n.getData().getCoordinate() - min);
-        }
-
-    }
-
-    private void optimizeMedian(ArrayList<Node<NodeData, EdgeData>> layers[]) {
-
-        // Downsweep
-        for (int i = 1; i < layers.length; i++) {
-
-            ArrayList<Node<NodeData, EdgeData>> processingList = layers[i];
-            ArrayList<Node<NodeData, EdgeData>> alreadyAssigned = new ArrayList<Node<NodeData, EdgeData>>();
-            for (Node<NodeData, EdgeData> n : processingList) {
-
-
-                ArrayList<Node<NodeData, EdgeData>> preds = new ArrayList<Node<NodeData, EdgeData>>(n.getPredecessors());
-                int pos = n.getData().getCoordinate();
-                if (preds.size() > 0) {
-
-                    Collections.sort(preds, new Comparator<Node<NodeData, EdgeData>>() {
-
-                        public int compare(Node<NodeData, EdgeData> o1, Node<NodeData, EdgeData> o2) {
-                            return o1.getData().getCoordinate() - o2.getData().getCoordinate();
-                        }
-                    });
-
-                    if (preds.size() % 2 == 0) {
-                        assert preds.size() >= 2;
-                        pos = (preds.get(preds.size() / 2).getData().getCoordinate() - calcRelativeCoordinate(preds.get(preds.size() / 2), n) + preds.get(preds.size() / 2 - 1).getData().getCoordinate() - calcRelativeCoordinate(preds.get(preds.size() / 2 - 1), n)) / 2;
-                    } else {
-                        assert preds.size() >= 1;
-                        pos = preds.get(preds.size() / 2).getData().getCoordinate() - calcRelativeCoordinate(preds.get(preds.size() / 2), n);
-                    }
-                }
-
-                tryAdding(alreadyAssigned, n, pos);
-            }
-        }
-        // Upsweep
-        for (int i = layers.length - 2; i >= 0; i--) {
-            ArrayList<Node<NodeData, EdgeData>> processingList = layers[i];
-            ArrayList<Node<NodeData, EdgeData>> alreadyAssigned = new ArrayList<Node<NodeData, EdgeData>>();
-            for (Node<NodeData, EdgeData> n : processingList) {
-
-                ArrayList<Node<NodeData, EdgeData>> succs = new ArrayList<Node<NodeData, EdgeData>>(n.getSuccessors());
-                int pos = n.getData().getCoordinate();
-                if (succs.size() > 0) {
-
-                    Collections.sort(succs, new Comparator<Node<NodeData, EdgeData>>() {
-
-                        public int compare(Node<NodeData, EdgeData> o1, Node<NodeData, EdgeData> o2) {
-                            return o1.getData().getCoordinate() - o2.getData().getCoordinate();
-                        }
-                    });
-
-                    if (succs.size() % 2 == 0) {
-                        assert succs.size() >= 2;
-                        pos = (succs.get(succs.size() / 2).getData().getCoordinate() - calcRelativeCoordinate(n, succs.get(succs.size() / 2)) + succs.get(succs.size() / 2 - 1).getData().getCoordinate() - calcRelativeCoordinate(n, succs.get(succs.size() / 2 - 1))) / 2;
-                    } else {
-                        assert succs.size() >= 1;
-                        pos = succs.get(succs.size() / 2).getData().getCoordinate() - calcRelativeCoordinate(n, succs.get(succs.size() / 2));
-                    }
-                }
-
-                tryAdding(alreadyAssigned, n, pos);
-            }
-        }
-    }
-
-    private int median(ArrayList<Integer> arr) {
-        assert arr.size() > 0;
-        Collections.sort(arr);
-        if (arr.size() % 2 == 0) {
-            return (arr.get(arr.size() / 2) + arr.get(arr.size() / 2 - 1)) / 2;
-        } else {
-            return arr.get(arr.size() / 2);
-        }
-    }
-
-    private int calcRelativeCoordinate(Node<NodeData, EdgeData> n, Node<NodeData, EdgeData> succ) {
-
-        if (n.getData().isDummy() && succ.getData().isDummy()) {
-            return 0;
-        }
-
-        int pos = 0;
-        int pos2 = 0;
-        ArrayList<Integer> coords2 = new ArrayList<Integer>();
-        ArrayList<Integer> coords = new ArrayList<Integer>();
-        /*if(!n.getData().isDummy())*/ {
-            for (Edge<NodeData, EdgeData> e : n.getOutEdges()) {
-
-                //System.out.println("reversed: " + e.getData().isReversed());
-                if (e.getDest() == succ) {
-
-                    if (e.getData().isReversed()) {
-                        if (!n.getData().isDummy()) {
-                            coords.add(e.getData().getRelativeEnd().x);
-                        }
-
-                        if (!succ.getData().isDummy()) {
-                            coords2.add(e.getData().getRelativeStart().x);
-                        }
-                    } else {
-                        if (!n.getData().isDummy()) {
-                            coords.add(e.getData().getRelativeStart().x);
-                        }
-
-                        if (!succ.getData().isDummy()) {
-                            coords2.add(e.getData().getRelativeEnd().x);
-                        }
-                    }
-                }
-            }
-
-            // assert coords.size() > 0;
-            if (!n.getData().isDummy()) {
-                pos = median(coords);
-            }
-
-            if (!succ.getData().isDummy()) {
-                pos2 = median(coords2);
-            }
-        }
-        //System.out.println("coords=" + coords);
-        //System.out.println("coords2=" + coords2);
-
-        return pos - pos2;
-    }
-
-    private boolean intersect(int v1, int w1, int v2, int w2) {
-        if (v1 >= v2 && v1 < v2 + w2) {
-            return true;
-        }
-        if (v1 + w1 > v2 && v1 + w1 < v2 + w2) {
-            return true;
-        }
-        if (v1 < v2 && v1 + w1 > v2) {
-            return true;
-        }
-        return false;
-    }
-
-    private boolean intersect(Node<NodeData, EdgeData> n1, Node<NodeData, EdgeData> n2) {
-        return intersect(n1.getData().getCoordinate(), n1.getData().getWidth() + OFFSET, n2.getData().getCoordinate(), n2.getData().getWidth() + OFFSET);
-    }
-
-    private void tryAdding(List<Node<NodeData, EdgeData>> alreadyAssigned, Node<NodeData, EdgeData> node, int pos) {
-
-        boolean doesIntersect = false;
-        node.getData().setCoordinate(pos);
-        for (Node<NodeData, EdgeData> n : alreadyAssigned) {
-            if (n.getData().getCoordinate() + n.getData().getWidth() < pos) {
-                break;
-            } else if (intersect(node, n)) {
-                doesIntersect = true;
-                break;
-            }
-
-        }
-
-        if (!doesIntersect) {
-
-            // Everything fine, just place the node
-            int z = 0;
-            for (Node<NodeData, EdgeData> n : alreadyAssigned) {
-                if (pos > n.getData().getCoordinate()) {
-                    break;
-                }
-                z++;
-            }
-
-            if (z == -1) {
-                z = alreadyAssigned.size();
-            }
-
-
-            if (ASSERT) {
-                assert !findOverlap(alreadyAssigned, node);
-            }
-            alreadyAssigned.add(z, node);
-
-        } else {
-
-            assert alreadyAssigned.size() > 0;
-
-            // Search for alternative location
-            int minOffset = Integer.MAX_VALUE;
-            int minIndex = -1;
-            int minPos = 0;
-            int w = node.getData().getWidth() + OFFSET;
-
-            // Try top-most
-            minIndex = 0;
-            minPos = alreadyAssigned.get(0).getData().getCoordinate() + alreadyAssigned.get(0).getData().getWidth() + OFFSET;
-            minOffset = Math.abs(minPos - pos);
-
-            // Try bottom-most
-            Node<NodeData, EdgeData> lastNode = alreadyAssigned.get(alreadyAssigned.size() - 1);
-            int lastPos = lastNode.getData().getCoordinate() - w;
-            int lastOffset = Math.abs(lastPos - pos);
-            if (lastOffset < minOffset) {
-                minPos = lastPos;
-                minOffset = lastOffset;
-                minIndex = alreadyAssigned.size();
-            }
-
-            // Try between
-            for (int i = 0; i < alreadyAssigned.size() - 1; i++) {
-                Node<NodeData, EdgeData> curNode = alreadyAssigned.get(i);
-                Node<NodeData, EdgeData> nextNode = alreadyAssigned.get(i + 1);
-
-                int start = nextNode.getData().getCoordinate() + nextNode.getData().getWidth() + OFFSET;
-                int end = curNode.getData().getCoordinate() - OFFSET;
-
-                int bestPoss = end - node.getData().getWidth();
-                if (bestPoss < pos && pos - bestPoss > minOffset) {
-                    // No better solution possible => break
-                    break;
-                }
-
-                if (end - start >= node.getData().getWidth()) {
-                    // Node could fit here
-                    int cand1 = start;
-                    int cand2 = end - node.getData().getWidth();
-                    int off1 = Math.abs(cand1 - pos);
-                    int off2 = Math.abs(cand2 - pos);
-                    if (off1 < minOffset) {
-                        minPos = cand1;
-                        minOffset = off1;
-                        minIndex = i + 1;
-                    }
-
-                    if (off2 < minOffset) {
-                        minPos = cand2;
-                        minOffset = off2;
-                        minIndex = i + 1;
-                    }
-                }
-            }
-
-            assert minIndex != -1;
-            node.getData().setCoordinate(minPos);
-            if (ASSERT) {
-                assert !findOverlap(alreadyAssigned, node);
-            }
-            alreadyAssigned.add(minIndex, node);
-        }
-
-    }
-
-    private boolean findOverlap(List<Node<NodeData, EdgeData>> nodes, Node<NodeData, EdgeData> node) {
-
-        for (Node<NodeData, EdgeData> n1 : nodes) {
-            if (intersect(n1, node)) {
-                return true;
-            }
-        }
-
-        return false;
-    }
-
-    private int evaluateSolution() {
-
-        int sum = 0;
-        for (Edge<NodeData, EdgeData> e : graph.getEdges()) {
-            Node<NodeData, EdgeData> source = e.getSource();
-            Node<NodeData, EdgeData> dest = e.getDest();
-            int offset = 0;
-            offset = Math.abs(source.getData().getCoordinate() - dest.getData().getCoordinate());
-            sum += offset;
-        }
-
-        return sum;
-    }
-
-    private void crossingReduction(ArrayList<Node<NodeData, EdgeData>> layers[]) {
-
-        for (int i = 0; i < layers.length - 1; i++) {
-
-            ArrayList<Node<NodeData, EdgeData>> curNodes = layers[i];
-            ArrayList<Node<NodeData, EdgeData>> nextNodes = layers[i + 1];
-            for (Node<NodeData, EdgeData> n : curNodes) {
-                for (Node<NodeData, EdgeData> succ : n.getSuccessors()) {
-                    if (ASSERT) {
-                        assert nextNodes.contains(succ);
-                    }
-                    nextNodes.remove(succ);
-                    nextNodes.add(succ);
-                }
-            }
-
-        }
-
-    }
-
-    private void removeCycles(Set<Node<NodeData, EdgeData>> rootNodes) {
-        final List<Edge<NodeData, EdgeData>> reversedEdges = new ArrayList<Edge<NodeData, EdgeData>>();
-
-
-        int removedCount = 0;
-        int reversedCount = 0;
-
-        Graph.DFSTraversalVisitor visitor = graph.new DFSTraversalVisitor() {
-
-            @Override
-            public boolean visitEdge(Edge<NodeData, EdgeData> e, boolean backEdge) {
-                if (backEdge) {
-                    if (ASSERT) {
-                        assert !reversedEdges.contains(e);
-                    }
-                    reversedEdges.add(e);
-                    e.getData().setReversed(!e.getData().isReversed());
-                }
-
-                return e.getData().isImportant();
-            }
-        };
-        Set<Node<NodeData, EdgeData>> nodes = new HashSet<Node<NodeData, EdgeData>>();
-        nodes.addAll(rootNodes);
-
-        assert nodes.size() > 0;
-
-        this.graph.traverseDFS(nodes, visitor);
-
-        for (Edge<NodeData, EdgeData> e : reversedEdges) {
-            if (e.isSelfLoop()) {
-                e.remove();
-                removedCount++;
-            } else {
-                e.reverse();
-                reversedCount++;
-            }
-        }
-    }
-
-    private boolean checkRemoveCycles() {
-        return !graph.hasCycles();
-    }
-    // Only used by assignLayers
-    private int maxLayerTemp;
-
-    private int assignLayers(Set<Node<NodeData, EdgeData>> rootNodes, Set<? extends Vertex> firstLayerHints,
-            Set<? extends Vertex> lastLayerHints) {
-        this.maxLayerTemp = -1;
-        for (Node<NodeData, EdgeData> n : graph.getNodes()) {
-            n.getData().setLayer(-1);
-        }
-
-        Graph.BFSTraversalVisitor traverser = graph.new BFSTraversalVisitor() {
-
-            @Override
-            public void visitNode(Node<NodeData, EdgeData> n, int depth) {
-                if (depth > n.getData().getLayer()) {
-                    n.getData().setLayer(depth);
-                    maxLayerTemp = Math.max(maxLayerTemp, depth);
-                }
-            }
-        };
-
-        for (Node<NodeData, EdgeData> n : rootNodes) {
-            if (n.getData().getLayer() == -1) {
-                this.graph.traverseBFS(n, traverser, true);
-            }
-        }
-
-        for (Vertex v : firstLayerHints) {
-            assert nodeMap.containsKey(v);
-            nodeMap.get(v).getData().setLayer(0);
-        }
-
-        for (Vertex v : lastLayerHints) {
-            assert nodeMap.containsKey(v);
-            nodeMap.get(v).getData().setLayer(maxLayerTemp);
-        }
-
-        return maxLayerTemp;
-    }
-
-    private boolean checkAssignLayers() {
-
-        for (Edge<NodeData, EdgeData> e : graph.getEdges()) {
-            Node<NodeData, EdgeData> source = e.getSource();
-            Node<NodeData, EdgeData> dest = e.getDest();
-
-
-            if (source.getData().getLayer() >= dest.getData().getLayer()) {
-                return false;
-            }
-        }
-        int maxLayer = 0;
-        for (Node<NodeData, EdgeData> n : graph.getNodes()) {
-            assert n.getData().getLayer() >= 0;
-            if (n.getData().getLayer() > maxLayer) {
-                maxLayer = n.getData().getLayer();
-            }
-        }
-
-        int countPerLayer[] = new int[maxLayer + 1];
-        for (Node<NodeData, EdgeData> n : graph.getNodes()) {
-            countPerLayer[n.getData().getLayer()]++;
-        }
-
-        if (TRACE) {
-            System.out.println("Number of layers: " + maxLayer);
-        }
-        return true;
-    }
-}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/Timing.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/HierarchicalLayout/src/com/sun/hotspot/igv/hierarchicallayout/Timing.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Layout/nbproject/project.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Layout/nbproject/project.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,2 +1,2 @@
-javac.source=1.5
-javac.compilerargs=-Xlint -Xlint:-serial
+javac.source=1.7
+javac.compilerargs=-Xlint -Xlint:-serial
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Layout/src/com/sun/hotspot/igv/layout/Cluster.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Layout/src/com/sun/hotspot/igv/layout/Cluster.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -37,6 +37,4 @@
     public void setBounds(Rectangle r);
 
     public Set<? extends Cluster> getSuccessors();
-
-    public Set<? extends Cluster> getPredecessors();
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Layout/src/com/sun/hotspot/igv/layout/LayoutGraph.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Layout/src/com/sun/hotspot/igv/layout/LayoutGraph.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,11 +23,7 @@
  */
 package com.sun.hotspot.igv.layout;
 
-import java.util.HashSet;
-import java.util.HashMap;
-import java.util.Set;
-import java.util.SortedSet;
-import java.util.TreeSet;
+import java.util.*;
 
 /**
  *
@@ -49,10 +45,10 @@
         this.links = links;
         assert verify();
 
-        vertices = new TreeSet<Vertex>();
-        portLinks = new HashMap<Port, Set<Link>>();
-        inputPorts = new HashMap<Vertex, Set<Port>>();
-        outputPorts = new HashMap<Vertex, Set<Port>>();
+        vertices = new TreeSet<>();
+        portLinks = new HashMap<>(links.size());
+        inputPorts = new HashMap<>(links.size());
+        outputPorts = new HashMap<>(links.size());
 
         for (Link l : links) {
             Port p = l.getFrom();
@@ -76,7 +72,7 @@
             }
 
             if (!portLinks.containsKey(p)) {
-                HashSet<Link> hashSet = new HashSet<Link>(3);
+                HashSet<Link> hashSet = new HashSet<>(3);
                 portLinks.put(p, hashSet);
             }
 
@@ -152,7 +148,7 @@
     //   whole graph is visited.
     public Set<Vertex> findRootVertices(Set<Vertex> startingRoots) {
 
-        Set<Vertex> notRootSet = new HashSet<Vertex>();
+        Set<Vertex> notRootSet = new HashSet<>();
         for (Vertex v : startingRoots) {
             if (!notRootSet.contains(v)) {
                 markNotRoot(notRootSet, v, v);
@@ -174,7 +170,7 @@
             }
         }
 
-        Set<Vertex> result = new HashSet<Vertex>();
+        Set<Vertex> result = new HashSet<>();
         for (Vertex v : tmpVertices) {
             if (!notRootSet.contains(v)) {
                 result.add(v);
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Layout/src/com/sun/hotspot/igv/layout/LayoutManager.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Layout/src/com/sun/hotspot/igv/layout/LayoutManager.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -33,7 +33,7 @@
 
     public void doLayout(LayoutGraph graph);
 
-    public void doLayout(LayoutGraph graph, Set<? extends Vertex> firstLayerHint, Set<? extends Vertex> lastLayerHint, Set<? extends Link> importantLinks);
+    public void doLayout(LayoutGraph graph, Set<? extends Link> importantLinks);
 
     public void doRouting(LayoutGraph graph);
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Layout/src/com/sun/hotspot/igv/layout/Link.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Layout/src/com/sun/hotspot/igv/layout/Link.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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,6 +36,8 @@
 
     public Port getTo();
 
+    public boolean isVIP();
+
     public List<Point> getControlPoints();
 
     public void setControlPoints(List<Point> list);
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Layout/src/com/sun/hotspot/igv/layout/Port.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Layout/src/com/sun/hotspot/igv/layout/Port.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Layout/src/com/sun/hotspot/igv/layout/Vertex.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Layout/src/com/sun/hotspot/igv/layout/Vertex.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -32,8 +32,6 @@
  */
 public interface Vertex extends Comparable<Vertex> {
 
-    public Cluster getCluster();
-
     public Dimension getSize();
 
     public Point getPosition();
@@ -41,4 +39,6 @@
     public void setPosition(Point p);
 
     public boolean isRoot();
+
+    public Cluster getCluster();
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/NetworkConnection/nbproject/genfiles.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/NetworkConnection/nbproject/genfiles.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,8 +1,5 @@
-build.xml.data.CRC32=f8e21cb6
-build.xml.script.CRC32=a265137e
-build.xml.stylesheet.CRC32=79c3b980
 # This file is used by a NetBeans-based IDE to track changes in generated files such as build-impl.xml.
 # Do not edit this file. You may delete it but then the IDE will never regenerate such files for you.
-nbproject/build-impl.xml.data.CRC32=f8e21cb6
-nbproject/build-impl.xml.script.CRC32=36f3138c
-nbproject/build-impl.xml.stylesheet.CRC32=deb65f65
+nbproject/build-impl.xml.data.CRC32=5a0e591e
+nbproject/build-impl.xml.script.CRC32=4c38ce23
+nbproject/build-impl.xml.stylesheet.CRC32=e50cf570@2.62.1
--- a/hotspot/src/share/tools/IdealGraphVisualizer/NetworkConnection/nbproject/project.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/NetworkConnection/nbproject/project.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,2 +1,2 @@
-javac.source=1.5
-javac.compilerargs=-Xlint -Xlint:-serial
+javac.source=1.7
+javac.compilerargs=-Xlint -Xlint:-serial
--- a/hotspot/src/share/tools/IdealGraphVisualizer/NetworkConnection/nbproject/project.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/NetworkConnection/nbproject/project.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -27,7 +27,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>6.11.1.1</specification-version>
+                        <specification-version>7.30.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -35,7 +35,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>7.5.1</specification-version>
+                        <specification-version>7.18.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -43,7 +43,15 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>7.10.1.1</specification-version>
+                        <specification-version>8.14.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.util.lookup</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>8.6.1</specification-version>
                     </run-dependency>
                 </dependency>
             </module-dependencies>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/NetworkConnection/src/META-INF/services/com.sun.hotspot.igv.data.services.GroupReceiver	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,1 +0,0 @@
-com.sun.hotspot.igv.connection.Server
\ No newline at end of file
--- a/hotspot/src/share/tools/IdealGraphVisualizer/NetworkConnection/src/com/sun/hotspot/igv/connection/Client.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/NetworkConnection/src/com/sun/hotspot/igv/connection/Client.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2007, 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,73 +24,48 @@
  */
 package com.sun.hotspot.igv.connection;
 
-import com.sun.hotspot.igv.data.Group;
-import com.sun.hotspot.igv.data.services.GroupCallback;
+import com.sun.hotspot.igv.data.GraphDocument;
+import com.sun.hotspot.igv.data.serialization.BinaryParser;
 import com.sun.hotspot.igv.data.serialization.Parser;
-import com.sun.hotspot.igv.data.Properties.RegexpPropertyMatcher;
+import com.sun.hotspot.igv.data.services.GroupCallback;
 import java.io.IOException;
-import java.io.InputStream;
-import java.net.Socket;
-import javax.swing.JTextField;
+import java.nio.channels.SocketChannel;
 import org.openide.util.Exceptions;
-import org.openide.xml.XMLUtil;
-import org.xml.sax.InputSource;
-import org.xml.sax.SAXException;
-import org.xml.sax.XMLReader;
 
-/**
- *
- * @author Thomas Wuerthinger
- */
-public class Client implements Runnable, GroupCallback {
+public class Client implements Runnable {
+    private final boolean binary;
+    private final SocketChannel socket;
+    private final GraphDocument rootDocument;
+    private final GroupCallback callback;
 
-    private Socket socket;
-    private JTextField networkTextField;
-    private GroupCallback callback;
-
-    public Client(Socket socket, JTextField networkTextField, GroupCallback callback) {
+    public Client(SocketChannel socket, GraphDocument rootDocument, GroupCallback callback, boolean  binary) {
         this.callback = callback;
         this.socket = socket;
-        this.networkTextField = networkTextField;
+        this.binary = binary;
+        this.rootDocument = rootDocument;
     }
 
+    @Override
     public void run() {
 
         try {
-            InputStream inputStream = socket.getInputStream();
-
-            if (networkTextField.isEnabled()) {
-
-                socket.getOutputStream().write('y');
-                InputSource is = new InputSource(inputStream);
-
-                try {
-                    XMLReader reader = XMLUtil.createXMLReader();
-                    Parser parser = new Parser(this);
-                    parser.parse(reader, is, null);
-                } catch (SAXException ex) {
-                    ex.printStackTrace();
-                }
+            final SocketChannel channel = socket;
+            channel.configureBlocking(true);
+            if (binary) {
+                new BinaryParser(channel, null, rootDocument, callback).parse();
             } else {
-                socket.getOutputStream().write('n');
+                // signal readiness to client VM (old protocol)
+                channel.socket().getOutputStream().write('y');
+                new Parser(channel, null, callback).parse();
             }
-
-            socket.close();
         } catch (IOException ex) {
             Exceptions.printStackTrace(ex);
-        }
-    }
-
-    public void started(final Group g) {
-        try {
-            RegexpPropertyMatcher matcher = new RegexpPropertyMatcher("name", ".*" + networkTextField.getText() + ".*");
-            if (g.getProperties().selectSingle(matcher) != null && networkTextField.isEnabled()) {
-                socket.getOutputStream().write('y');
-                callback.started(g);
-            } else {
-                socket.getOutputStream().write('n');
+        } finally {
+            try {
+                socket.close();
+            } catch (IOException ex) {
+                Exceptions.printStackTrace(ex);
             }
-        } catch (IOException e) {
         }
     }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/NetworkConnection/src/com/sun/hotspot/igv/connection/Server.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/NetworkConnection/src/com/sun/hotspot/igv/connection/Server.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2007, 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,17 +24,15 @@
  */
 package com.sun.hotspot.igv.connection;
 
-import com.sun.hotspot.igv.data.Group;
+import com.sun.hotspot.igv.data.GraphDocument;
 import com.sun.hotspot.igv.data.services.GroupCallback;
-import com.sun.hotspot.igv.data.services.GroupReceiver;
 import com.sun.hotspot.igv.settings.Settings;
-import java.awt.Component;
 import java.io.IOException;
-import java.net.ServerSocket;
-import java.net.Socket;
+import java.net.InetSocketAddress;
+import java.nio.channels.ServerSocketChannel;
+import java.nio.channels.SocketChannel;
 import java.util.prefs.PreferenceChangeEvent;
 import java.util.prefs.PreferenceChangeListener;
-import javax.swing.SwingUtilities;
 import org.openide.DialogDisplayer;
 import org.openide.NotifyDescriptor;
 import org.openide.util.RequestProcessor;
@@ -43,54 +41,26 @@
  *
  * @author Thomas Wuerthinger
  */
-public class Server implements GroupCallback, GroupReceiver, PreferenceChangeListener {
-
-    private javax.swing.JPanel jPanel1;
-    private javax.swing.JCheckBox networkCheckBox;
-    private javax.swing.JTextField networkTextField;
-    private ServerSocket serverSocket;
-    private GroupCallback callback;
+public class Server implements PreferenceChangeListener {
+    private final boolean binary;
+    private ServerSocketChannel serverSocket;
+    private final GraphDocument rootDocument;
+    private final GroupCallback callback;
     private int port;
     private Runnable serverRunnable;
 
-    public Component init(GroupCallback callback) {
-
+    public Server(GraphDocument rootDocument, GroupCallback callback, boolean binary) {
+        this.binary = binary;
+        this.rootDocument = rootDocument;
         this.callback = callback;
-
-        jPanel1 = new javax.swing.JPanel();
-        networkTextField = new javax.swing.JTextField();
-        networkCheckBox = new javax.swing.JCheckBox();
-
-
-        jPanel1.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));
-        jPanel1.setLayout(new java.awt.BorderLayout(10, 10));
-        jPanel1.add(networkTextField, java.awt.BorderLayout.CENTER);
-
-        networkCheckBox.setSelected(true);
-        org.openide.awt.Mnemonics.setLocalizedText(networkCheckBox, "Receive when name contains");
-        networkCheckBox.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 0, 0, 0));
-        networkCheckBox.setMargin(new java.awt.Insets(0, 0, 0, 0));
-        networkCheckBox.addChangeListener(new javax.swing.event.ChangeListener() {
-
-            public void stateChanged(javax.swing.event.ChangeEvent evt) {
-                networkCheckBoxChanged(evt);
-            }
-        });
-        jPanel1.add(networkCheckBox, java.awt.BorderLayout.WEST);
-        networkCheckBox.getAccessibleContext().setAccessibleName("Read from network when name contains");
-
         initializeNetwork();
         Settings.get().addPreferenceChangeListener(this);
-        return jPanel1;
     }
 
-    private void networkCheckBoxChanged(javax.swing.event.ChangeEvent evt) {
-        networkTextField.setEnabled(networkCheckBox.isSelected());
-    }
-
+    @Override
     public void preferenceChange(PreferenceChangeEvent e) {
 
-        int curPort = Integer.parseInt(Settings.get().get(Settings.PORT, Settings.PORT_DEFAULT));
+        int curPort = Integer.parseInt(Settings.get().get(binary ? Settings.PORT_BINARY : Settings.PORT, binary ? Settings.PORT_BINARY_DEFAULT : Settings.PORT_DEFAULT));
         if (curPort != port) {
             initializeNetwork();
         }
@@ -98,30 +68,32 @@
 
     private void initializeNetwork() {
 
-        int curPort = Integer.parseInt(Settings.get().get(Settings.PORT, Settings.PORT_DEFAULT));
+        int curPort = Integer.parseInt(Settings.get().get(binary ? Settings.PORT_BINARY : Settings.PORT, binary ? Settings.PORT_BINARY_DEFAULT : Settings.PORT_DEFAULT));
         this.port = curPort;
         try {
-            serverSocket = new java.net.ServerSocket(curPort);
-        } catch (IOException ex) {
-            NotifyDescriptor message = new NotifyDescriptor.Message("Could not create server. Listening for incoming data is disabled.", NotifyDescriptor.ERROR_MESSAGE);
+            serverSocket = ServerSocketChannel.open();
+            serverSocket.bind(new InetSocketAddress(curPort));
+        } catch (Throwable ex) {
+            NotifyDescriptor message = new NotifyDescriptor.Message("Could not create server. Listening for incoming binary data is disabled.", NotifyDescriptor.ERROR_MESSAGE);
             DialogDisplayer.getDefault().notifyLater(message);
             return;
         }
 
         Runnable runnable = new Runnable() {
 
+            @Override
             public void run() {
                 while (true) {
                     try {
-                        Socket clientSocket = serverSocket.accept();
+                        SocketChannel clientSocket = serverSocket.accept();
                         if (serverRunnable != this) {
                             clientSocket.close();
                             return;
                         }
-                        RequestProcessor.getDefault().post(new Client(clientSocket, networkTextField, Server.this), 0, Thread.MAX_PRIORITY);
+                        RequestProcessor.getDefault().post(new Client(clientSocket, rootDocument, callback, binary), 0, Thread.MAX_PRIORITY);
                     } catch (IOException ex) {
                         serverSocket = null;
-                        NotifyDescriptor message = new NotifyDescriptor.Message("Error during listening for incoming connections. Listening for incoming data is disabled.", NotifyDescriptor.ERROR_MESSAGE);
+                        NotifyDescriptor message = new NotifyDescriptor.Message("Error during listening for incoming connections. Listening for incoming binary data is disabled.", NotifyDescriptor.ERROR_MESSAGE);
                         DialogDisplayer.getDefault().notifyLater(message);
                         return;
                     }
@@ -133,13 +105,4 @@
 
         RequestProcessor.getDefault().post(runnable, 0, Thread.MAX_PRIORITY);
     }
-
-    public void started(final Group g) {
-        SwingUtilities.invokeLater(new Runnable() {
-
-            public void run() {
-                callback.started(g);
-            }
-        });
-    }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/README	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,40 +0,0 @@
-The Ideal Graph Visualizer is a tool developed to help examine the
-intermediate representation of C2 which is commonly referred to as the
-"ideal graph".  It was developed in collaboration with the University
-of Linz in Austria and has been included as part of hotspot since that
-was the primary target of the tool.  The tool itself is fairly general
-with only a few modules that contain C2 specific elements.
-
-The tool is built on top of the NetBeans 6.1 rich client
-infrastructure and so requires NetBeans to build.  It currently
-requires Java 6 to run as it needs support for JavaScript for its
-filtering mechanism and assumes it's built into the platform.  It
-should build out of the box with NetBeans 6.1 and Java 6 or later.
-It's possible to run it on 1.5 by including Rhino on the classpath
-though that currently isn't working correctly.  Support for exporting
-graphs as SVG can be enabled by adding batik to the classpath which
-isn't included by default.  It can be built on top of NetBeans 6.0 if
-you change the required modules to be platform7 instead of platform8.
-
-The JVM support is controlled by the flag -XX:PrintIdealGraphLevel=#
-where # is:
-
-  0: no output, the default
-  1: dumps graph after parsing, before matching, and final code.
-     also dumps graph for failed compiles, if available
-  2: more detail, including after loop opts
-  3: even more detail
-  4: prints graph after parsing every bytecode (very slow)
-
-By default the JVM expects that it will connect to a visualizer on the
-local host on port 4444.  This can be configured using the options
--XX:PrintIdealGraphAddress= and -XX:PrintIdealGraphPort=.
-PrintIdealGraphAddress can actually be a hostname.
-
-Alternatively the output can be sent to a file using
--XX:PrintIdealGraphFile=filename.  Each compiler thread will get it's
-own file with unique names being generated by adding a number onto the
-provided file name.
-
-More information about the tool is available at
-http://wikis.sun.com/display/HotSpotInternals/IdealGraphVisualizer.
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/README.md	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,50 @@
+# Overview
+
+The Ideal Graph Visualizer is a tool developed to help examine the intermediate
+representation of C2 which is commonly referred to as the "ideal graph". It was
+developed in collaboration with the University of Linz in Austria and has been
+included as part of hotspot since that was the primary target of the tool. The
+tool itself is fairly general with only a few modules that contain C2 specific
+elements.
+
+The tool is built on top of the NetBeans 7 rich client infrastructure and so
+requires NetBeans to build. It currently requires at least Java 6 to run as it
+needs support for JavaScript for its filtering mechanism and assumes it's built
+into the platform.  It should build out of the box with NetBeans 7.0 and Java 6
+or later.
+
+# Building and Running
+
+The build system used for IGV is ant. To download all required libraries and
+build IGV, issue `ant build`. To run IGV, use the `igv.sh` command; it will put
+all log messages generated by the run to the file `.igv.log`. To see all log
+messages generated during an IGV run, use `ant run`.
+
+# Usage
+
+The JVM support is controlled by the flag `-XX:PrintIdealGraphLevel=#` where `#`
+is:
+
+* 0: no output, the default
+* 1: dumps graph after parsing, before matching, and final code (also dumps
+     graphs for failed compilations, if available)
+* 2: more detail, including after loop opts
+* 3: even more detail
+* 4: prints graph after parsing every bytecode (very slow)
+
+By default the JVM expects that it will connect to a visualizer on the local
+host on port 4444. This can be configured using the options
+`-XX:PrintIdealGraphAddress=` and `-XX:PrintIdealGraphPort=`.
+`PrintIdealGraphAddress` can actually be a hostname.
+
+It is advisable to run the JVM with background compilation disabled (-Xbatch).
+Compilations going on in the background may be cancelled when the VM terminates,
+which can lead to incomplete dumps being sent to IGV.
+
+Alternatively the output can be sent to a file using
+`-XX:PrintIdealGraphFile=filename`. Each compiler thread will get it's own file
+with unique names being generated by adding a number onto the provided file
+name.
+
+More information about the tool is available at
+https://wikis.oracle.com/display/HotSpotInternals/IdealGraphVisualizer.
--- a/hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/build.xml	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,8 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!-- You may freely edit this file. See harness/README in the NetBeans platform -->
-<!-- for some information on what you could do (e.g. targets to override). -->
-<!-- If you delete this file and reopen the project it will be recreated. -->
-<project name="com.sun.hotspot.igv.rhino" default="netbeans" basedir=".">
-    <description>Builds, tests, and runs the project com.sun.hotspot.igv.rhino.</description>
-    <import file="nbproject/build-impl.xml"/>
-</project>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/manifest.mf	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,6 +0,0 @@
-Manifest-Version: 1.0
-OpenIDE-Module: com.sun.hotspot.igv.rhino
-OpenIDE-Module-Layer: com/sun/hotspot/igv/rhino/layer.xml
-OpenIDE-Module-Localizing-Bundle: com/sun/hotspot/igv/rhino/Bundle.properties
-OpenIDE-Module-Specification-Version: 1.0
-
--- a/hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/nbproject/build-impl.xml	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,30 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-*** GENERATED FROM project.xml - DO NOT EDIT  ***
-***         EDIT ../build.xml INSTEAD         ***
--->
-<project name="com.sun.hotspot.igv.rhino-impl" basedir="..">
-    <property file="nbproject/private/suite-private.properties"/>
-    <property file="nbproject/suite.properties"/>
-    <fail unless="suite.dir">You must set 'suite.dir' to point to your containing module suite</fail>
-    <property file="${suite.dir}/nbproject/private/platform-private.properties"/>
-    <property file="${suite.dir}/nbproject/platform.properties"/>
-    <macrodef name="property" uri="http://www.netbeans.org/ns/nb-module-project/2">
-        <attribute name="name"/>
-        <attribute name="value"/>
-        <sequential>
-            <property name="@{name}" value="${@{value}}"/>
-        </sequential>
-    </macrodef>
-    <property file="${user.properties.file}"/>
-    <nbmproject2:property name="harness.dir" value="nbplatform.${nbplatform.active}.harness.dir" xmlns:nbmproject2="http://www.netbeans.org/ns/nb-module-project/2"/>
-    <nbmproject2:property name="netbeans.dest.dir" value="nbplatform.${nbplatform.active}.netbeans.dest.dir" xmlns:nbmproject2="http://www.netbeans.org/ns/nb-module-project/2"/>
-    <fail message="You must define 'nbplatform.${nbplatform.active}.harness.dir'">
-        <condition>
-            <not>
-                <available file="${harness.dir}" type="dir"/>
-            </not>
-        </condition>
-    </fail>
-    <import file="${harness.dir}/build.xml"/>
-</project>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/nbproject/genfiles.properties	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,8 +0,0 @@
-build.xml.data.CRC32=0c3e7912
-build.xml.script.CRC32=44d0050c
-build.xml.stylesheet.CRC32=79c3b980
-# This file is used by a NetBeans-based IDE to track changes in generated files such as build-impl.xml.
-# Do not edit this file. You may delete it but then the IDE will never regenerate such files for you.
-nbproject/build-impl.xml.data.CRC32=0c3e7912
-nbproject/build-impl.xml.script.CRC32=7aab3f52
-nbproject/build-impl.xml.stylesheet.CRC32=deb65f65
--- a/hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/nbproject/project.properties	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,2 +0,0 @@
-javac.source=1.5
-javac.compilerargs=-Xlint -Xlint:-serial
--- a/hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/nbproject/project.xml	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,31 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<project xmlns="http://www.netbeans.org/ns/project/1">
-    <type>org.netbeans.modules.apisupport.project</type>
-    <configuration>
-        <data xmlns="http://www.netbeans.org/ns/nb-module-project/3">
-            <code-name-base>com.sun.hotspot.igv.rhino</code-name-base>
-            <suite-component/>
-            <module-dependencies>
-                <dependency>
-                    <code-name-base>com.sun.hotspot.igv.filter</code-name-base>
-                    <build-prerequisite/>
-                    <compile-dependency/>
-                    <run-dependency>
-                        <specification-version>1.0</specification-version>
-                    </run-dependency>
-                </dependency>
-                <dependency>
-                    <code-name-base>com.sun.hotspot.igv.graph</code-name-base>
-                    <build-prerequisite/>
-                    <compile-dependency/>
-                    <run-dependency>
-                        <specification-version>1.0</specification-version>
-                    </run-dependency>
-                </dependency>
-            </module-dependencies>
-            <public-packages>
-                <package>com.sun.hotspot.igv.rhino</package>
-            </public-packages>
-        </data>
-    </configuration>
-</project>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/nbproject/suite.properties	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,1 +0,0 @@
-suite.dir=${basedir}/..
--- a/hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/src/META-INF/services/com.sun.hotspot.igv.filter.ScriptEngineAbstraction	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,1 +0,0 @@
-com.sun.hotspot.igv.rhino.RhinoScriptEngine
\ No newline at end of file
--- a/hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/src/com/sun/hotspot/igv/rhino/Bundle.properties	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,1 +0,0 @@
-OpenIDE-Module-Name=RhinoScriptEngineProxy
--- a/hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/src/com/sun/hotspot/igv/rhino/RhinoScriptEngine.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,85 +0,0 @@
-/*
- * Copyright (c) 1998, 2007, Oracle and/or its affiliates. All rights reserved.
- * 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 com.sun.hotspot.igv.rhino;
-
-import com.sun.hotspot.igv.filter.ScriptEngineAbstraction;
-import com.sun.hotspot.igv.graph.Diagram;
-import java.lang.reflect.Constructor;
-import java.lang.reflect.InvocationTargetException;
-import java.lang.reflect.Method;
-
-/**
- *
- * @author Thomas Wuerthinger
- */
-public class RhinoScriptEngine implements ScriptEngineAbstraction {
-
-    private String jsHelperText;
-    private Constructor importer;
-    private Method scope_put;
-    private Method cx_evaluateString;
-    private Method context_enter;
-    private Method context_exit;
-
-    public boolean initialize(String s) {
-        this.jsHelperText = s;
-        Class importerTopLevel = null;
-        try {
-            ClassLoader cl = RhinoScriptEngine.class.getClassLoader();
-            Class context = cl.loadClass("org.mozilla.javascript.Context");
-            Class scriptable = cl.loadClass("org.mozilla.javascript.Scriptable");
-            importerTopLevel = cl.loadClass("org.mozilla.javascript.ImporterTopLevel");
-            importer = importerTopLevel.getDeclaredConstructor(context);
-            scope_put = importerTopLevel.getMethod("put", new Class[]{String.class, scriptable, Object.class});
-            cx_evaluateString = context.getDeclaredMethod("evaluateString", new Class[]{scriptable, String.class, String.class, Integer.TYPE, Object.class});
-            context_enter = context.getDeclaredMethod("enter", new Class[0]);
-            context_exit = context.getDeclaredMethod("exit", new Class[0]);
-            return true;
-        } catch (NoSuchMethodException nsme) {
-            return false;
-        } catch (ClassNotFoundException cnfe) {
-            return false;
-        }
-    }
-
-    public void execute(Diagram d, String code) {
-        try {
-            Object cx = context_enter.invoke(null, (Object[]) null);
-            try {
-                Object scope = importer.newInstance(cx);
-                scope_put.invoke(scope, "IO", scope, System.out);
-                scope_put.invoke(scope, "graph", scope, d);
-                cx_evaluateString.invoke(cx, scope, jsHelperText, "jsHelper.js", 1, null);
-                cx_evaluateString.invoke(cx, scope, code, "<cmd>", 1, null);
-            } finally {
-                // Exit from the context.
-                context_exit.invoke(null, (Object[]) null);
-            }
-        } catch (InvocationTargetException iae) {
-        } catch (IllegalAccessException iae) {
-        } catch (InstantiationException iae) {
-        }
-    }
-}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/RhinoScriptEngineProxy/src/com/sun/hotspot/igv/rhino/layer.xml	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,4 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!DOCTYPE filesystem PUBLIC "-//NetBeans//DTD Filesystem 1.1//EN" "http://www.netbeans.org/dtds/filesystem-1_1.dtd">
-<filesystem>
-</filesystem>
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/SelectionCoordinator/build.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,8 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- You may freely edit this file. See harness/README in the NetBeans platform -->
+<!-- for some information on what you could do (e.g. targets to override). -->
+<!-- If you delete this file and reopen the project it will be recreated. -->
+<project name="com.sun.hotspot.igv.selectioncoordinator" default="netbeans" basedir=".">
+    <description>Builds, tests, and runs the project com.sun.hotspot.igv.selectioncoordinator.</description>
+    <import file="nbproject/build-impl.xml"/>
+</project>
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/SelectionCoordinator/manifest.mf	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,5 @@
+Manifest-Version: 1.0
+OpenIDE-Module: com.sun.hotspot.igv.selectioncoordinator
+OpenIDE-Module-Localizing-Bundle: com/sun/hotspot/igv/selectioncoordinator/Bundle.properties
+OpenIDE-Module-Specification-Version: 1.0
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/SelectionCoordinator/nbproject/build-impl.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,45 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+*** GENERATED FROM project.xml - DO NOT EDIT  ***
+***         EDIT ../build.xml INSTEAD         ***
+-->
+<project name="com.sun.hotspot.igv.selectioncoordinator-impl" basedir="..">
+    <fail message="Please build using Ant 1.7.1 or higher.">
+        <condition>
+            <not>
+                <antversion atleast="1.7.1"/>
+            </not>
+        </condition>
+    </fail>
+    <property file="nbproject/private/suite-private.properties"/>
+    <property file="nbproject/suite.properties"/>
+    <fail unless="suite.dir">You must set 'suite.dir' to point to your containing module suite</fail>
+    <property file="${suite.dir}/nbproject/private/platform-private.properties"/>
+    <property file="${suite.dir}/nbproject/platform.properties"/>
+    <macrodef name="property" uri="http://www.netbeans.org/ns/nb-module-project/2">
+        <attribute name="name"/>
+        <attribute name="value"/>
+        <sequential>
+            <property name="@{name}" value="${@{value}}"/>
+        </sequential>
+    </macrodef>
+    <macrodef name="evalprops" uri="http://www.netbeans.org/ns/nb-module-project/2">
+        <attribute name="property"/>
+        <attribute name="value"/>
+        <sequential>
+            <property name="@{property}" value="@{value}"/>
+        </sequential>
+    </macrodef>
+    <property file="${user.properties.file}"/>
+    <nbmproject2:property name="harness.dir" value="nbplatform.${nbplatform.active}.harness.dir" xmlns:nbmproject2="http://www.netbeans.org/ns/nb-module-project/2"/>
+    <nbmproject2:property name="nbplatform.active.dir" value="nbplatform.${nbplatform.active}.netbeans.dest.dir" xmlns:nbmproject2="http://www.netbeans.org/ns/nb-module-project/2"/>
+    <nbmproject2:evalprops property="cluster.path.evaluated" value="${cluster.path}" xmlns:nbmproject2="http://www.netbeans.org/ns/nb-module-project/2"/>
+    <fail message="Path to 'platform' cluster missing in $${cluster.path} property or using corrupt Netbeans Platform (missing harness).">
+        <condition>
+            <not>
+                <contains string="${cluster.path.evaluated}" substring="platform"/>
+            </not>
+        </condition>
+    </fail>
+    <import file="${harness.dir}/build.xml"/>
+</project>
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/SelectionCoordinator/nbproject/genfiles.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,5 @@
+# This file is used by a NetBeans-based IDE to track changes in generated files such as build-impl.xml.
+# Do not edit this file. You may delete it but then the IDE will never regenerate such files for you.
+nbproject/build-impl.xml.data.CRC32=13553862
+nbproject/build-impl.xml.script.CRC32=3db87c68
+nbproject/build-impl.xml.stylesheet.CRC32=238281d1@2.67.1
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/SelectionCoordinator/nbproject/platform.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,129 @@
+# Deprecated since 5.0u1; for compatibility with 5.0:
+disabled.clusters=\
+    apisupport1,\
+    gsf1,\
+    harness,\
+    java2,\
+    nb6.1,\
+    profiler3
+disabled.modules=\
+    org.apache.xml.resolver,\
+    org.netbeans.api.debugger,\
+    org.netbeans.api.xml,\
+    org.netbeans.core.execution,\
+    org.netbeans.core.ide,\
+    org.netbeans.core.multiview,\
+    org.netbeans.core.nativeaccess,\
+    org.netbeans.core.output2,\
+    org.netbeans.insane,\
+    org.netbeans.lib.cvsclient,\
+    org.netbeans.libs.commons_logging,\
+    org.netbeans.libs.freemarker,\
+    org.netbeans.libs.ini4j,\
+    org.netbeans.libs.jna,\
+    org.netbeans.libs.jsch,\
+    org.netbeans.libs.jsr223,\
+    org.netbeans.libs.lucene,\
+    org.netbeans.libs.svnClientAdapter,\
+    org.netbeans.libs.xerces,\
+    org.netbeans.modules.applemenu,\
+    org.netbeans.modules.autoupdate.services,\
+    org.netbeans.modules.autoupdate.ui,\
+    org.netbeans.modules.classfile,\
+    org.netbeans.modules.core.kit,\
+    org.netbeans.modules.db,\
+    org.netbeans.modules.db.core,\
+    org.netbeans.modules.db.drivers,\
+    org.netbeans.modules.db.kit,\
+    org.netbeans.modules.db.mysql,\
+    org.netbeans.modules.db.sql.editor,\
+    org.netbeans.modules.db.sql.visualeditor,\
+    org.netbeans.modules.dbapi,\
+    org.netbeans.modules.defaults,\
+    org.netbeans.modules.diff,\
+    org.netbeans.modules.editor.bookmarks,\
+    org.netbeans.modules.editor.bracesmatching,\
+    org.netbeans.modules.editor.codetemplates,\
+    org.netbeans.modules.editor.completion,\
+    org.netbeans.modules.editor.errorstripe,\
+    org.netbeans.modules.editor.errorstripe.api,\
+    org.netbeans.modules.editor.guards,\
+    org.netbeans.modules.editor.highlights,\
+    org.netbeans.modules.editor.macros,\
+    org.netbeans.modules.editor.plain,\
+    org.netbeans.modules.editor.plain.lib,\
+    org.netbeans.modules.editor.structure,\
+    org.netbeans.modules.extbrowser,\
+    org.netbeans.modules.favorites,\
+    org.netbeans.modules.gototest,\
+    org.netbeans.modules.httpserver,\
+    org.netbeans.modules.ide.kit,\
+    org.netbeans.modules.image,\
+    org.netbeans.modules.javahelp,\
+    org.netbeans.modules.jumpto,\
+    org.netbeans.modules.languages,\
+    org.netbeans.modules.languages.bat,\
+    org.netbeans.modules.languages.diff,\
+    org.netbeans.modules.languages.manifest,\
+    org.netbeans.modules.languages.sh,\
+    org.netbeans.modules.lexer.editorbridge,\
+    org.netbeans.modules.lexer.nbbridge,\
+    org.netbeans.modules.localhistory,\
+    org.netbeans.modules.masterfs,\
+    org.netbeans.modules.mercurial,\
+    org.netbeans.modules.progress.ui,\
+    org.netbeans.modules.project.ant,\
+    org.netbeans.modules.project.libraries,\
+    org.netbeans.modules.projectui,\
+    org.netbeans.modules.projectuiapi,\
+    org.netbeans.modules.properties,\
+    org.netbeans.modules.properties.syntax,\
+    org.netbeans.modules.refactoring.api,\
+    org.netbeans.modules.schema2beans,\
+    org.netbeans.modules.sendopts,\
+    org.netbeans.modules.server,\
+    org.netbeans.modules.servletapi,\
+    org.netbeans.modules.subversion,\
+    org.netbeans.modules.tasklist.kit,\
+    org.netbeans.modules.tasklist.projectint,\
+    org.netbeans.modules.tasklist.todo,\
+    org.netbeans.modules.tasklist.ui,\
+    org.netbeans.modules.templates,\
+    org.netbeans.modules.timers,\
+    org.netbeans.modules.usersguide,\
+    org.netbeans.modules.utilities,\
+    org.netbeans.modules.utilities.project,\
+    org.netbeans.modules.versioning,\
+    org.netbeans.modules.versioning.system.cvss,\
+    org.netbeans.modules.versioning.util,\
+    org.netbeans.modules.web.flyingsaucer,\
+    org.netbeans.modules.xml,\
+    org.netbeans.modules.xml.axi,\
+    org.netbeans.modules.xml.catalog,\
+    org.netbeans.modules.xml.core,\
+    org.netbeans.modules.xml.lexer,\
+    org.netbeans.modules.xml.multiview,\
+    org.netbeans.modules.xml.retriever,\
+    org.netbeans.modules.xml.schema.completion,\
+    org.netbeans.modules.xml.schema.model,\
+    org.netbeans.modules.xml.tax,\
+    org.netbeans.modules.xml.text,\
+    org.netbeans.modules.xml.tools,\
+    org.netbeans.modules.xml.wsdl.model,\
+    org.netbeans.modules.xml.xam,\
+    org.netbeans.modules.xml.xdm,\
+    org.netbeans.modules.xsl,\
+    org.netbeans.spi.debugger.ui,\
+    org.netbeans.spi.editor.hints,\
+    org.netbeans.spi.navigator,\
+    org.netbeans.spi.palette,\
+    org.netbeans.spi.tasklist,\
+    org.netbeans.spi.viewmodel,\
+    org.netbeans.swing.dirchooser,\
+    org.openide.compat,\
+    org.openide.util.enumerations
+enabled.clusters=\
+    ide9,\
+    platform8
+nbjdk.active=default
+nbplatform.active=default
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/SelectionCoordinator/nbproject/project.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,2 @@
+javac.source=1.7
+javac.compilerargs=-Xlint -Xlint:-serial
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/SelectionCoordinator/nbproject/project.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,23 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://www.netbeans.org/ns/project/1">
+    <type>org.netbeans.modules.apisupport.project</type>
+    <configuration>
+        <data xmlns="http://www.netbeans.org/ns/nb-module-project/3">
+            <code-name-base>com.sun.hotspot.igv.selectioncoordinator</code-name-base>
+            <suite-component/>
+            <module-dependencies>
+                <dependency>
+                    <code-name-base>com.sun.hotspot.igv.data</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>1.0</specification-version>
+                    </run-dependency>
+                </dependency>
+            </module-dependencies>
+            <public-packages>
+                <package>com.sun.hotspot.igv.selectioncoordinator</package>
+            </public-packages>
+        </data>
+    </configuration>
+</project>
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/SelectionCoordinator/nbproject/suite.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,1 @@
+suite.dir=${basedir}/..
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/SelectionCoordinator/src/com/sun/hotspot/igv/selectioncoordinator/Bundle.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,1 @@
+OpenIDE-Module-Name=SelectionCoordinator
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/SelectionCoordinator/src/com/sun/hotspot/igv/selectioncoordinator/SelectionCoordinator.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,139 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+
+package com.sun.hotspot.igv.selectioncoordinator;
+
+import com.sun.hotspot.igv.data.ChangedEvent;
+import java.util.Collections;
+import java.util.HashSet;
+import java.util.Set;
+
+/**
+ *
+ * @author Thomas
+ */
+public class SelectionCoordinator {
+
+    private static SelectionCoordinator singleInstance = new SelectionCoordinator();
+    private Set<Object> selectedObjects;
+    private Set<Object> highlightedObjects;
+    private ChangedEvent<SelectionCoordinator> selectedChangedEvent;
+    private ChangedEvent<SelectionCoordinator> highlightedChangedEvent;
+
+    public static SelectionCoordinator getInstance() {
+        return singleInstance;
+    }
+
+    private SelectionCoordinator() {
+        selectedChangedEvent = new ChangedEvent<>(this);
+        highlightedChangedEvent = new ChangedEvent<>(this);
+        selectedObjects = new HashSet<>();
+        highlightedObjects = new HashSet<>();
+    }
+
+    public Set<Object> getSelectedObjects() {
+        return Collections.unmodifiableSet(selectedObjects);
+    }
+
+    public Set<Object> getHighlightedObjects() {
+        return Collections.unmodifiableSet(highlightedObjects);
+    }
+
+    public ChangedEvent<SelectionCoordinator> getHighlightedChangedEvent() {
+        return highlightedChangedEvent;
+    }
+
+    public ChangedEvent<SelectionCoordinator> getSelectedChangedEvent() {
+        return selectedChangedEvent;
+    }
+
+    public void addHighlighted(Object o) {
+        if (!highlightedObjects.contains(o)) {
+            highlightedObjects.add(o);
+            highlightedObjectsChanged();
+        }
+    }
+
+    public void removeHighlighted(Object o) {
+        if (highlightedObjects.contains(o)) {
+            highlightedObjects.remove(o);
+            highlightedObjectsChanged();
+        }
+    }
+
+    public void addAllHighlighted(Set<? extends Object> s) {
+        int oldSize = highlightedObjects.size();
+        highlightedObjects.addAll(s);
+        if (oldSize != highlightedObjects.size()) {
+            highlightedObjectsChanged();
+        }
+    }
+
+    public void removeAllHighlighted(Set<? extends Object> s) {
+        int oldSize = highlightedObjects.size();
+        highlightedObjects.removeAll(s);
+        if (oldSize != highlightedObjects.size()) {
+            highlightedObjectsChanged();
+        }
+    }
+
+    private void highlightedObjectsChanged() {
+        highlightedChangedEvent.fire();
+
+    }
+
+    public void addAllSelected(Set<? extends Object> s) {
+        int oldSize = selectedObjects.size();
+        selectedObjects.addAll(s);
+        if (oldSize != selectedObjects.size()) {
+            selectedObjectsChanged();
+        }
+    }
+
+    public void removeAllSelected(Set<? extends Object> s) {
+        int oldSize = selectedObjects.size();
+        selectedObjects.removeAll(s);
+        if (oldSize != selectedObjects.size()) {
+            selectedObjectsChanged();
+        }
+    }
+
+    public void setSelectedObjects(Set<? extends Object> s) {
+        assert s != null;
+        selectedObjects.clear();
+        selectedObjects.addAll(s);
+        selectedObjectsChanged();
+    }
+
+    private void selectedObjectsChanged() {
+        selectedChangedEvent.fire();
+    }
+
+    public void setHighlightedObjects(Set<? extends Object> s) {
+        assert s != null;
+        this.highlightedObjects.clear();
+        this.highlightedObjects.addAll(s);
+        highlightedObjectsChanged();
+    }
+}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/nbproject/project.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/nbproject/project.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,2 +1,2 @@
-javac.source=1.5
-javac.compilerargs=-Xlint -Xlint:-serial
+javac.source=1.7
+javac.compilerargs=-Xlint -Xlint:-serial
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/nbproject/project.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/nbproject/project.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -1,21 +1,29 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<project xmlns="http://www.netbeans.org/ns/project/1">
-    <type>org.netbeans.modules.apisupport.project</type>
-    <configuration>
-        <data xmlns="http://www.netbeans.org/ns/nb-module-project/3">
-            <code-name-base>com.sun.hotspot.igv.servercompiler</code-name-base>
-            <suite-component/>
-            <module-dependencies>
-                <dependency>
-                    <code-name-base>com.sun.hotspot.igv.data</code-name-base>
-                    <build-prerequisite/>
-                    <compile-dependency/>
-                    <run-dependency>
-                        <specification-version>1.0</specification-version>
-                    </run-dependency>
-                </dependency>
-            </module-dependencies>
-            <public-packages/>
-        </data>
-    </configuration>
-</project>
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://www.netbeans.org/ns/project/1">
+    <type>org.netbeans.modules.apisupport.project</type>
+    <configuration>
+        <data xmlns="http://www.netbeans.org/ns/nb-module-project/3">
+            <code-name-base>com.sun.hotspot.igv.servercompiler</code-name-base>
+            <suite-component/>
+            <module-dependencies>
+                <dependency>
+                    <code-name-base>com.sun.hotspot.igv.data</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>1.0</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>com.sun.hotspot.igv.graph</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>1.0</specification-version>
+                    </run-dependency>
+                </dependency>
+            </module-dependencies>
+            <public-packages/>
+        </data>
+    </configuration>
+</project>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/META-INF/services/com.sun.hotspot.igv.data.services.GroupOrganizer	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,1 +0,0 @@
-com.sun.hotspot.igv.servercompiler.JavaGroupOrganizer
\ No newline at end of file
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/JavaGroupOrganizer.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,200 +0,0 @@
-/*
- * Copyright (c) 1998, 2007, Oracle and/or its affiliates. All rights reserved.
- * 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 com.sun.hotspot.igv.servercompiler;
-
-import com.sun.hotspot.igv.data.Group;
-import com.sun.hotspot.igv.data.services.GroupOrganizer;
-import com.sun.hotspot.igv.data.Pair;
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.Comparator;
-import java.util.HashMap;
-import java.util.List;
-
-/**
- *
- * @author Thomas Wuerthinger
- */
-public class JavaGroupOrganizer implements GroupOrganizer {
-
-    public String getName() {
-        return "Java structure";
-    }
-
-    public List<Pair<String, List<Group>>> organize(List<String> subFolders, List<Group> groups) {
-
-        List<Pair<String, List<Group>>> result = new ArrayList<Pair<String, List<Group>>>();
-
-        if (subFolders.size() == 0) {
-            buildResult(result, groups, packageNameProvider);
-        } else if (subFolders.size() == 1) {
-            buildResult(result, groups, classNameProvider);
-        } else if (subFolders.size() == 2) {
-            for (Group g : groups) {
-                List<Group> children = new ArrayList<Group>();
-                children.add(g);
-                Pair<String, List<Group>> p = new Pair<String, List<Group>>();
-                p.setLeft(reducedNameProvider.getName(g));
-                p.setRight(children);
-                result.add(p);
-            }
-        } else {
-            result.add(new Pair<String, List<Group>>("", groups));
-        }
-
-        return result;
-    }
-
-    private void buildResult(List<Pair<String, List<Group>>> result, List<Group> groups, NameProvider provider) {
-        HashMap<String, List<Group>> map = new HashMap<String, List<Group>>();
-        for (Group g : groups) {
-            String s = provider.getName(g);
-
-            if (!map.containsKey(s)) {
-                List<Group> list = new ArrayList<Group>();
-                Pair<String, List<Group>> pair = new Pair<String, List<Group>>(s, list);
-                result.add(pair);
-                map.put(s, list);
-            }
-
-            List<Group> curList = map.get(s);
-            curList.add(g);
-        }
-
-        Collections.sort(result, new Comparator<Pair<String, List<Group>>>() {
-
-            public int compare(Pair<String, List<Group>> a, Pair<String, List<Group>> b) {
-                return a.getLeft().compareTo(b.getLeft());
-            }
-        });
-    }
-
-    private static interface NameProvider {
-
-        public String getName(Group g);
-    }
-    private NameProvider reducedNameProvider = new NameProvider() {
-
-        public String getName(Group g) {
-            String name = g.getName();
-            assert name != null : "name of group must be set!";
-            final String noReducedName = name;
-
-            int firstPoint = name.indexOf(".");
-            if (firstPoint == -1) {
-                return noReducedName;
-            }
-
-            int firstParenthese = name.indexOf("(");
-            if (firstParenthese == -1 || firstParenthese < firstPoint) {
-                return noReducedName;
-            }
-
-            int current = firstPoint;
-            while (current > 0 && name.charAt(current) != ' ') {
-                current--;
-            }
-
-            String tmp = name.substring(0, firstParenthese);
-            int lastPoint = tmp.lastIndexOf(".");
-            if (lastPoint == -1) {
-                return noReducedName;
-            }
-
-            name = name.substring(0, current + 1) + name.substring(lastPoint + 1);
-            return name;
-        }
-    };
-    private NameProvider packageNameProvider = new NameProvider() {
-
-        public String getName(Group g) {
-            String name = g.getName();
-            assert name != null : "name of group must be set!";
-            final String noPackage = "<default>";
-
-            int firstPoint = name.indexOf(".");
-            if (firstPoint == -1) {
-                return noPackage;
-            }
-
-            int firstParenthese = name.indexOf("(");
-            if (firstParenthese == -1 || firstParenthese < firstPoint) {
-                return noPackage;
-            }
-
-            int current = firstPoint;
-            while (current > 0 && name.charAt(current) != ' ') {
-                current--;
-            }
-
-            String fullClassName = name.substring(current + 1, firstParenthese);
-            int lastPoint = fullClassName.lastIndexOf(".");
-            if (lastPoint == -1) {
-                return noPackage;
-            }
-            lastPoint = fullClassName.lastIndexOf(".", lastPoint - 1);
-            if (lastPoint == -1) {
-                return noPackage;
-            }
-
-            String packageName = fullClassName.substring(0, lastPoint);
-            return packageName;
-        }
-    };
-    private NameProvider classNameProvider = new NameProvider() {
-
-        public String getName(Group g) {
-            String name = g.getName();
-            assert name != null : "name of group must be set!";
-
-            final String noClass = "<noclass>";
-
-            int firstPoint = name.indexOf(".");
-            if (firstPoint == -1) {
-                return noClass;
-            }
-
-            int firstParenthese = name.indexOf("(");
-            if (firstParenthese == -1 || firstParenthese < firstPoint) {
-                return noClass;
-            }
-
-            int current = firstPoint;
-            while (current > 0 && name.charAt(current) != ' ') {
-                current--;
-            }
-
-            String fullClassName = name.substring(current + 1, firstParenthese);
-            int lastPoint = fullClassName.lastIndexOf(".");
-            if (lastPoint == -1) {
-                return noClass;
-            }
-            int lastlastPoint = fullClassName.lastIndexOf(".", lastPoint - 1);
-
-            String className = fullClassName.substring(lastlastPoint + 1, lastPoint);
-            return className;
-        }
-    };
-}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/ServerCompilerScheduler.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/ServerCompilerScheduler.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2007, 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
@@ -29,17 +29,7 @@
 import com.sun.hotspot.igv.data.InputGraph;
 import com.sun.hotspot.igv.data.InputNode;
 import com.sun.hotspot.igv.data.services.Scheduler;
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.Collections;
-import java.util.Comparator;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-import java.util.Stack;
-import java.util.Vector;
+import java.util.*;
 
 /**
  *
@@ -50,8 +40,8 @@
     private static class Node {
 
         public InputNode inputNode;
-        public Set<Node> succs = new HashSet<Node>();
-        public List<Node> preds = new ArrayList<Node>();
+        public Set<Node> succs = new HashSet<>();
+        public List<Node> preds = new ArrayList<>();
         public InputBlock block;
         public boolean isBlockProjection;
         public boolean isBlockStart;
@@ -65,6 +55,7 @@
     private InputBlock[][] commonDominator;
     private static final Comparator<InputEdge> edgeComparator = new Comparator<InputEdge>() {
 
+        @Override
         public int compare(InputEdge o1, InputEdge o2) {
             return o1.getToIndex() - o2.getToIndex();
         }
@@ -72,13 +63,13 @@
 
     public void buildBlocks() {
 
-        blocks = new Vector<InputBlock>();
+        blocks = new Vector<>();
         Node root = findRoot();
         if (root == null) {
             return;
         }
-        Stack<Node> stack = new Stack<Node>();
-        Set<Node> visited = new HashSet<Node>();
+        Stack<Node> stack = new Stack<>();
+        Set<Node> visited = new HashSet<>();
         stack.add(root);
         int blockCount = 0;
         InputBlock rootBlock = null;
@@ -93,7 +84,7 @@
 
             if (!visited.contains(parent)) {
                 visited.add(parent);
-                InputBlock block = new InputBlock(graph, "" + blockCount);
+                InputBlock block = graph.addBlock(Integer.toString(blockCount));
                 blocks.add(block);
                 if (parent == root) {
                     rootBlock = block;
@@ -111,7 +102,12 @@
                         p = parent;
                         break;
                     }
+
                     p = p.preds.get(0);
+                    if (p == proj) {
+                        // Cycle, stop
+                        break;
+                    }
 
                     if (p.block == null) {
                         p.block = block;
@@ -125,7 +121,7 @@
                                 n = n.preds.get(0);
                             }
                             if (n.block != null) {
-                                n.block.addSuccessor(block);
+                                graph.addBlockEdge(n.block, block);
                             }
                         }
                     }
@@ -136,12 +132,12 @@
                         for (Node n2 : n.succs) {
 
                             if (n2 != parent && n2.block != null && n2.block != rootBlock) {
-                                block.addSuccessor(n2.block);
+                                graph.addBlockEdge(block, n2.block);
                             }
                         }
                     } else {
                         if (n != parent && n.block != null && n.block != rootBlock) {
-                            block.addSuccessor(n.block);
+                            graph.addBlockEdge(block, n.block);
                         }
                     }
                 }
@@ -161,7 +157,7 @@
                 }
 
                 if (pushed == 0 && p == root) {
-                // TODO: special handling when root backedges are not built yet
+                    // TODO: special handling when root backedges are not built yet
                 }
             }
         }
@@ -174,7 +170,7 @@
         }
 
         int z = 0;
-        blockIndex = new HashMap<InputBlock, Integer>();
+        blockIndex = new HashMap<>(blocks.size());
         for (InputBlock b : blocks) {
             blockIndex.put(b, z);
             z++;
@@ -185,20 +181,25 @@
         return n.getProperties().get("block");
     }
 
+    @Override
     public Collection<InputBlock> schedule(InputGraph graph) {
+        if (graph.getNodes().isEmpty()) {
+            return Collections.emptyList();
+        }
+
         if (graph.getBlocks().size() > 0) {
-            Collection<InputNode> tmpNodes = new ArrayList<InputNode>(graph.getNodes());
+            Collection<InputNode> tmpNodes = new ArrayList<>(graph.getNodes());
             for (InputNode n : tmpNodes) {
                 String block = getBlockName(n);
                 if (graph.getBlock(n) == null) {
-                    graph.getBlock(block).addNode(n);
+                    graph.getBlock(block).addNode(n.getId());
                     assert graph.getBlock(n) != null;
                 }
             }
             return graph.getBlocks();
         } else {
-            nodes = new ArrayList<Node>();
-            inputNodeToNode = new HashMap<InputNode, Node>();
+            nodes = new ArrayList<>();
+            inputNodeToNode = new HashMap<>(graph.getNodes().size());
 
             this.graph = graph;
             buildUpGraph();
@@ -207,7 +208,16 @@
             buildCommonDominators();
             scheduleLatest();
 
+            InputBlock noBlock = null;
             for (InputNode n : graph.getNodes()) {
+                if (graph.getBlock(n) == null) {
+                    if (noBlock == null) {
+                        noBlock = graph.addBlock("(no block)");
+                        blocks.add(noBlock);
+                    }
+
+                    graph.setBlock(n, noBlock);
+                }
                 assert graph.getBlock(n) != null;
             }
 
@@ -215,15 +225,17 @@
         }
     }
 
-    public void scheduleLatest() {
-
-
+    private void scheduleLatest() {
         Node root = findRoot();
+        if(root == null) {
+            assert false : "No root found!";
+            return;
+        }
 
         // Mark all nodes reachable in backward traversal from root
-        Set<Node> reachable = new HashSet<Node>();
+        Set<Node> reachable = new HashSet<>();
         reachable.add(root);
-        Stack<Node> stack = new Stack<Node>();
+        Stack<Node> stack = new Stack<>();
         stack.push(root);
         while (!stack.isEmpty()) {
             Node cur = stack.pop();
@@ -235,7 +247,7 @@
             }
         }
 
-        Set<Node> unscheduled = new HashSet<Node>();
+        Set<Node> unscheduled = new HashSet<>();
         for (Node n : this.nodes) {
             if (n.block == null && reachable.contains(n)) {
                 unscheduled.add(n);
@@ -245,7 +257,7 @@
         while (unscheduled.size() > 0) {
             boolean progress = false;
 
-            Set<Node> newUnscheduled = new HashSet<Node>();
+            Set<Node> newUnscheduled = new HashSet<>();
             for (Node n : unscheduled) {
 
                 InputBlock block = null;
@@ -285,7 +297,7 @@
             }
         }
 
-        Set<Node> curReachable = new HashSet<Node>(reachable);
+        Set<Node> curReachable = new HashSet<>(reachable);
         for (Node n : curReachable) {
             if (n.block != null) {
                 for (Node s : n.succs) {
@@ -300,7 +312,7 @@
 
     private void markWithBlock(Node n, InputBlock b, Set<Node> reachable) {
         assert !reachable.contains(n);
-        Stack<Node> stack = new Stack<Node>();
+        Stack<Node> stack = new Stack<>();
         stack.push(n);
         n.block = b;
         b.addNode(n.inputNode.getId());
@@ -356,7 +368,7 @@
         if (ba == bb) {
             return ba;
         }
-        Set<InputBlock> visited = new HashSet<InputBlock>();
+        Set<InputBlock> visited = new HashSet<>();
         while (ba != null) {
             visited.add(ba);
             ba = dominatorMap.get(ba);
@@ -374,12 +386,12 @@
     }
 
     public void buildDominators() {
-        dominatorMap = new HashMap<InputBlock, InputBlock>();
+        dominatorMap = new HashMap<>(graph.getBlocks().size());
         if (blocks.size() == 0) {
             return;
         }
-        Vector<BlockIntermediate> intermediate = new Vector<BlockIntermediate>();
-        Map<InputBlock, BlockIntermediate> map = new HashMap<InputBlock, BlockIntermediate>();
+        Vector<BlockIntermediate> intermediate = new Vector<>(graph.getBlocks().size());
+        Map<InputBlock, BlockIntermediate> map = new HashMap<>(graph.getBlocks().size());
         int z = 0;
         for (InputBlock b : blocks) {
             BlockIntermediate bi = new BlockIntermediate();
@@ -390,16 +402,16 @@
             bi.parent = -1;
             bi.label = z;
             bi.ancestor = -1;
-            bi.pred = new ArrayList<Integer>();
-            bi.bucket = new ArrayList<Integer>();
+            bi.pred = new ArrayList<>();
+            bi.bucket = new ArrayList<>();
             intermediate.add(bi);
             map.put(b, bi);
             z++;
         }
-        Stack<Integer> stack = new Stack<Integer>();
+        Stack<Integer> stack = new Stack<>();
         stack.add(0);
 
-        Vector<BlockIntermediate> array = new Vector<BlockIntermediate>();
+        Vector<BlockIntermediate> array = new Vector<>();
         intermediate.get(0).dominator = 0;
 
         int n = 0;
@@ -538,15 +550,30 @@
     }
 
     private Node findRoot() {
+        Node minNode = null;
+        Node alternativeRoot = null;
 
-        for (Node n : nodes) {
-            InputNode inputNode = n.inputNode;
-            if (inputNode.getProperties().get("name").equals("Root")) {
-                return n;
+        for (Node node : nodes) {
+            InputNode inputNode = node.inputNode;
+            String s = inputNode.getProperties().get("name");
+            if (s != null && s.equals("Root")) {
+                return node;
+            }
+
+            if (alternativeRoot == null && node.preds.isEmpty()) {
+                alternativeRoot = node;
+            }
+
+            if (minNode == null || node.inputNode.getId() < minNode.inputNode.getId()) {
+                minNode = node;
             }
         }
 
-        return null;
+        if (alternativeRoot != null) {
+            return alternativeRoot;
+        } else {
+            return minNode;
+        }
     }
 
     public void buildUpGraph() {
@@ -562,7 +589,7 @@
             inputNodeToNode.put(n, node);
         }
 
-        Map<Integer, List<InputEdge>> edgeMap = new HashMap<Integer, List<InputEdge>>();
+        Map<Integer, List<InputEdge>> edgeMap = new HashMap<>(graph.getEdges().size());
         for (InputEdge e : graph.getEdges()) {
 
             int to = e.getTo();
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/color.filter	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/color.filter	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,18 @@
 colorize("name", ".*", yellow);
 colorize("name", "Catch.*", blue);
-
 colorize("name", "Region|Loop|CountedLoop|Root", red);
 colorize("name", "CProj|IfFalse|IfTrue|JProj|CatchProj", magenta);
+colorize("name", "Con.*", orange);
+colorize("name", "Parm|Proj", lightGray);
+
+// Nodes with bci
+colorize("bci", "..*", magenta);
+
+// Line style
+var f = new ColorFilter("Line Style filter");
+f.addRule(new ColorFilter.ColorRule(new MatcherSelector(new Properties.StringPropertyMatcher("type", "int:")), null, Color.BLUE, null));
+f.addRule(new ColorFilter.ColorRule(new MatcherSelector(new Properties.StringPropertyMatcher("type", "control")), null, Color.RED, null));
+f.addRule(new ColorFilter.ColorRule(new MatcherSelector(new Properties.StringPropertyMatcher("type", "memory")), null, Color.GREEN, null));
+f.addRule(new ColorFilter.ColorRule(new MatcherSelector(new Properties.StringPropertyMatcher("type", "tuple:")), null, Color.MAGENTA, null));
+f.addRule(new ColorFilter.ColorRule(new MatcherSelector(new Properties.StringPropertyMatcher("type", "bottom")), null, Color.LIGHT_GRAY, null));
+f.apply(graph);
\ No newline at end of file
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/combine.filter	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,4 +0,0 @@
-var f = new CombineFilter("Combine Filter");
-f.addRule(new CombineFilter.CombineRule(new Properties.RegexpPropertyMatcher("name", ".*"), new Properties.RegexpPropertyMatcher("name", "Proj|IfFalse|IfTrue|JProj|MachProj|JumpProj|CatchProj")));
-f.addRule(new CombineFilter.CombineRule(new Properties.RegexpPropertyMatcher("name", "Cmp.*"), new Properties.RegexpPropertyMatcher("name", "Bool")));
-f.apply(graph);
\ No newline at end of file
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/extendedColor.filter	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,3 +0,0 @@
-colorize("name", "Con.*", orange);
-colorize("name", "Parm|Proj", lightGray);
-colorize("bci", "..*", magenta);
\ No newline at end of file
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/linestyle.filter	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,7 +0,0 @@
-var f = new ColorFilter("Line Style filter");
-f.addRule(new ColorFilter.ColorRule(new MatcherSelector(new Properties.StringPropertyMatcher("type", "int:")), null, Color.BLUE, null));
-f.addRule(new ColorFilter.ColorRule(new MatcherSelector(new Properties.StringPropertyMatcher("type", "control")), null, Color.RED, null));
-f.addRule(new ColorFilter.ColorRule(new MatcherSelector(new Properties.StringPropertyMatcher("type", "memory")), null, Color.GREEN, null));
-f.addRule(new ColorFilter.ColorRule(new MatcherSelector(new Properties.StringPropertyMatcher("type", "tuple:")), null, Color.MAGENTA, null));
-f.addRule(new ColorFilter.ColorRule(new MatcherSelector(new Properties.StringPropertyMatcher("type", "bottom")), null, Color.LIGHT_GRAY, null));
-f.apply(graph);
\ No newline at end of file
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/onlyControlFlow.filter	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/onlyControlFlow.filter	Wed Jul 05 20:35:10 2017 +0200
@@ -20,5 +20,5 @@
     ), false
   )
 );
-f.addRule( new RemoveFilter.RemoveRule(new MatcherSelector(new Properties.RegexpPropertyMatcher("name", "Phi|Store.")), false));
+f.addRule(new RemoveFilter.RemoveRule(new MatcherSelector(new Properties.RegexpPropertyMatcher("name", "Phi|Store."))));
 f.apply(graph);
\ No newline at end of file
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/register.filter	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/register.filter	Wed Jul 05 20:35:10 2017 +0200
@@ -1,4 +1,5 @@
+// Register coloring
 colorize("reg", "EAX", green);
 colorize("reg", "EFLAGS", gray);
 colorize("reg", "EBP", orange);
-colorize("reg", "ECX", cyan);
+colorize("reg", "ECX", cyan);
\ No newline at end of file
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/remove.filter	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/remove.filter	Wed Jul 05 20:35:10 2017 +0200
@@ -1,1 +1,8 @@
-remove("dump_spec", "FramePtr|ReturnAdr|I_O"); 
\ No newline at end of file
+remove("dump_spec", "FramePtr|ReturnAdr|I_O"); 
+removeInputs("name", "Root");
+var f = new RemoveSelfLoopsFilter("Remove Self-Loops");
+f.apply(graph);
+removeInputs("name", "SafePoint|CallStaticJava|CallDynamicJava|CallJava|CallLeaf|CallRuntime|AbstractLock|CallLeafNoFP|Call|CallStaticJavaDirect", 5);
+removeInputs("name", "Unlock|Lock", 7);
+removeInputs("name", "Allocate", 7);
+removeInputs("name", "AllocateArray", 9);
\ No newline at end of file
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/removeMemory.filter	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,7 +0,0 @@
-
-//var f = new RemoveFilter("Remove Memory");
-//f.addRule(new RemoveFilter.RemoveRule(new MatcherSelector(new Properties.StringPropertyMatcher("dump_spec", "Memory")), false));
-//f.addRule(new RemoveFilter.RemoveRule(new AndSelector(new MatcherSelector(new Properties.StringPropertyMatcher("name", "Proj")), new MatcherSelector(new Properties.StringPropertyMatcher("type", "memory"))), false));
-//f.apply(graph);
-
-remove("dump_spec", "Memory");
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/removeRootInputs.filter	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,1 +0,0 @@
-removeInputs("name", "Root");
\ No newline at end of file
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/removeSafepointInputs.filter	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,4 +0,0 @@
-removeInputs("name", "SafePoint|CallStaticJava|CallDynamicJava|CallJava|CallLeaf|CallRuntime|AbstractLock|CallLeafNoFP|Call|CallStaticJavaDirect", 5);
-removeInputs("name", "Unlock|Lock", 7);
-removeInputs("name", "Allocate", 7);
-removeInputs("name", "AllocateArray", 9);
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/removeSelfLoops.filter	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,2 +0,0 @@
-var f = new RemoveSelfLoopsFilter("Remove Self-Loops");
-f.apply(graph);
\ No newline at end of file
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/split.filter	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,2 +0,0 @@
-split("name", "BoxLock");
-split("name", "(Con.*)|(loadCon.*)");
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/filters/structural.filter	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,6 @@
+var f = new CombineFilter("Combine Filter");
+f.addRule(new CombineFilter.CombineRule(new Properties.RegexpPropertyMatcher("name", ".*"), new Properties.RegexpPropertyMatcher("name", "Proj|IfFalse|IfTrue|JProj|MachProj|JumpProj|CatchProj")));
+f.addRule(new CombineFilter.CombineRule(new Properties.RegexpPropertyMatcher("name", "Cmp.*"), new Properties.RegexpPropertyMatcher("name", "Bool")));
+f.apply(graph);
+split("name", "BoxLock");
+split("name", "(Con.*)|(loadCon.*)", "[dump_spec]");
\ No newline at end of file
--- a/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/layer.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/ServerCompiler/src/com/sun/hotspot/igv/servercompiler/layer.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -2,60 +2,28 @@
 <!DOCTYPE filesystem PUBLIC "-//NetBeans//DTD Filesystem 1.1//EN" "http://www.netbeans.org/dtds/filesystem-1_1.dtd">
 <filesystem>
       <folder name="Filters">
-        <file name="Basic Coloring" url="filters/color.filter">
-            <attr name="enabled" boolvalue="true"/>
-        </file>
-        <file name="Matcher Flags Coloring" url="filters/matchingFlags.filter">
-            <attr name="enabled" boolvalue="true"/>
-            <attr name="after" stringvalue="Basic Coloring"/>
-        </file>
-        <file name="Register Coloring" url="filters/register.filter">
-            <attr name="enabled" boolvalue="true"/>
-            <attr name="after" stringvalue="Matcher Flags Coloring"/>
+        <file name="C2 Basic Coloring" url="filters/color.filter">
+            <attr name="enabled" boolvalue="false"/>
         </file>
-        <file name="Extended Coloring" url="filters/extendedColor.filter">
-            <attr name="enabled" boolvalue="true"/>
-            <attr name="after" stringvalue="Register Coloring"/>
-        </file>
-        <file name="Line Coloring" url="filters/linestyle.filter">
-            <attr name="enabled" boolvalue="true"/>
-            <attr name="after" stringvalue="Extended Coloring"/>
+        <file name="C2 Matcher Flags Coloring" url="filters/matchingFlags.filter">
+            <attr name="enabled" boolvalue="false"/>
+            <attr name="after" stringvalue="C2 Basic Coloring"/>
         </file>
-        <file name="Difference Coloring" url="filters/difference.filter">
-            <attr name="enabled" boolvalue="true"/>
-            <attr name="after" stringvalue="Line Coloring"/>
-        </file>
-        <file name="Only Control Flow" url="filters/onlyControlFlow.filter">
+        <file name="C2 Register Coloring" url="filters/register.filter">
             <attr name="enabled" boolvalue="false"/>
-            <attr name="after" stringvalue="Difference Coloring"/>
+            <attr name="after" stringvalue="C2 Matcher Flags Coloring"/>
         </file>
-        <file name="Remove FramePtr, I_O and Return Address" url="filters/remove.filter">
-            <attr name="enabled" boolvalue="true"/>
-            <attr name="after" stringvalue="Only Control Flow"/>
-        </file>
-        <file name="Remove Memory" url="filters/removeMemory.filter">
+        <file name="C2 Only Control Flow" url="filters/onlyControlFlow.filter">
             <attr name="enabled" boolvalue="false"/>
-            <attr name="after" stringvalue="Remove FramePtr, I_O and Return Address"/>
-        </file>
-        <file name="Remove Root Inputs" url="filters/removeRootInputs.filter">
-            <attr name="enabled" boolvalue="true"/>
-            <attr name="after" stringvalue="Remove Memory"/>
+            <attr name="after" stringvalue="C2 Register Coloring"/>
         </file>
-        <file name="Remove Safepoint Inputs" url="filters/removeSafepointInputs.filter">
-            <attr name="enabled" boolvalue="true"/>
-            <attr name="after" stringvalue="Remove Root Inputs"/>
-        </file>
-        <file name="Remove Self Loops" url="filters/removeSelfLoops.filter">
-            <attr name="enabled" boolvalue="true"/>
-            <attr name="after" stringvalue="Remove Safepoint Inputs"/>
+        <file name="C2 Remove Filter" url="filters/remove.filter">
+            <attr name="enabled" boolvalue="false"/>
+            <attr name="after" stringvalue="C2 Only Control Flow"/>
         </file>
-        <file name="Combine" url="filters/combine.filter">
-            <attr name="enabled" boolvalue="true"/>
-            <attr name="after" stringvalue="Remove Self Loops"/>
+        <file name="C2 Structural" url="filters/structural.filter">
+            <attr name="enabled" boolvalue="false"/>
+            <attr name="after" stringvalue="C2 Remove Filter"/>
         </file>
-        <file name="Split" url="filters/split.filter">
-            <attr name="enabled" boolvalue="true"/>
-            <attr name="after" stringvalue="Combine"/>
-        </file>
-    </folder>
+    </folder>	
 </filesystem>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Settings/nbproject/project.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Settings/nbproject/project.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,2 +1,2 @@
-javac.source=1.5
-javac.compilerargs=-Xlint -Xlint:-serial
+javac.source=1.7
+javac.compilerargs=-Xlint -Xlint:-serial
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Settings/nbproject/project.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Settings/nbproject/project.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -12,7 +12,7 @@
                     <compile-dependency/>
                     <run-dependency>
                         <release-version>1</release-version>
-                        <specification-version>1.4</specification-version>
+                        <specification-version>1.16.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -21,7 +21,7 @@
                     <compile-dependency/>
                     <run-dependency>
                         <release-version>1</release-version>
-                        <specification-version>1.5</specification-version>
+                        <specification-version>1.21.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -29,7 +29,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>6.11.0.1</specification-version>
+                        <specification-version>7.30.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -37,7 +37,15 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>7.9.0.1</specification-version>
+                        <specification-version>8.14.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.util.lookup</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>8.6.1</specification-version>
                     </run-dependency>
                 </dependency>
             </module-dependencies>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Settings/src/com/sun/hotspot/igv/settings/Settings.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Settings/src/com/sun/hotspot/igv/settings/Settings.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2007, 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
@@ -37,7 +37,9 @@
     public final static String NODE_WIDTH = "nodeWidth";
     public final static String NODE_WIDTH_DEFAULT = "100";
     public final static String PORT = "port";
+    public final static String PORT_BINARY = "portBinary";
     public final static String PORT_DEFAULT = "4444";
+    public final static String PORT_BINARY_DEFAULT = "4445";
     public final static String DIRECTORY = "directory";
     public final static String DIRECTORY_DEFAULT = System.getProperty("user.dir");
 
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Settings/src/com/sun/hotspot/igv/settings/ViewOptionsCategory.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Settings/src/com/sun/hotspot/igv/settings/ViewOptionsCategory.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -27,8 +27,8 @@
 import javax.swing.ImageIcon;
 import org.netbeans.spi.options.OptionsCategory;
 import org.netbeans.spi.options.OptionsPanelController;
+import org.openide.util.ImageUtilities;
 import org.openide.util.NbBundle;
-import org.openide.util.Utilities;
 
 /**
  *
@@ -38,17 +38,20 @@
 
     @Override
     public Icon getIcon() {
-        return new ImageIcon(Utilities.loadImage("com/sun/hotspot/igv/settings/settings.gif"));
+        return new ImageIcon(ImageUtilities.loadImage("com/sun/hotspot/igv/settings/settings.png"));
     }
 
+    @Override
     public String getCategoryName() {
         return NbBundle.getMessage(ViewOptionsCategory.class, "OptionsCategory_Name_View");
     }
 
+    @Override
     public String getTitle() {
         return NbBundle.getMessage(ViewOptionsCategory.class, "OptionsCategory_Title_View");
     }
 
+    @Override
     public OptionsPanelController create() {
         return new ViewOptionsPanelController();
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Settings/src/com/sun/hotspot/igv/settings/ViewOptionsPanelController.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Settings/src/com/sun/hotspot/igv/settings/ViewOptionsPanelController.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -40,40 +40,49 @@
     private final PropertyChangeSupport pcs = new PropertyChangeSupport(this);
     private boolean changed;
 
+    @Override
     public void update() {
         getPanel().load();
         changed = false;
     }
 
+    @Override
     public void applyChanges() {
         getPanel().store();
         changed = false;
     }
 
+    @Override
     public void cancel() {
     // need not do anything special, if no changes have been persisted yet
     }
 
+    @Override
     public boolean isValid() {
         return getPanel().valid();
     }
 
+    @Override
     public boolean isChanged() {
         return changed;
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return null; // new HelpCtx("...ID") if you have a help set
     }
 
+    @Override
     public JComponent getComponent(Lookup masterLookup) {
         return getPanel();
     }
 
+    @Override
     public void addPropertyChangeListener(PropertyChangeListener l) {
         pcs.addPropertyChangeListener(l);
     }
 
+    @Override
     public void removePropertyChangeListener(PropertyChangeListener l) {
         pcs.removePropertyChangeListener(l);
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Settings/src/com/sun/hotspot/igv/settings/ViewPanel.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Settings/src/com/sun/hotspot/igv/settings/ViewPanel.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Settings/src/com/sun/hotspot/igv/settings/layer.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Settings/src/com/sun/hotspot/igv/settings/layer.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -2,8 +2,10 @@
 <!DOCTYPE filesystem PUBLIC "-//NetBeans//DTD Filesystem 1.1//EN" "http://www.netbeans.org/dtds/filesystem-1_1.dtd">
 <filesystem>
     <folder name="OptionsDialog">
-        <file name="Advanced.instance_hidden"/>
-        <file name="General.instance_hidden"/>
-        <file name="com-sun-hotspot-igv-settings-ViewOptionsCategory.instance"/>
+      <!-- <file name="Advanced.instance_hidden"/>
+        <file name="General.instance_hidden"/>-->
+        <file name="com-sun-hotspot-igv-settings-ViewOptionsCategory.instance">
+            <attr name="position" intvalue="100" />
+        </file>
     </folder>
 </filesystem>
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Settings/src/com/sun/hotspot/igv/settings/settings.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/Settings/src/com/sun/hotspot/igv/settings/settings.png has changed
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Util/nbproject/project.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Util/nbproject/project.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,2 +1,2 @@
-javac.source=1.5
-javac.compilerargs=-Xlint -Xlint:-serial
+javac.source=1.7
+javac.compilerargs=-Xlint -Xlint:-serial
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Util/nbproject/project.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Util/nbproject/project.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -19,7 +19,15 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>2.9</specification-version>
+                        <specification-version>2.27.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.awt</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>7.39.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -27,7 +35,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>7.2.1.1</specification-version>
+                        <specification-version>7.20.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -35,7 +43,15 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>7.10.1.1</specification-version>
+                        <specification-version>8.14.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.util.lookup</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>8.6.1</specification-version>
                     </run-dependency>
                 </dependency>
             </module-dependencies>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/BoundedZoomAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/BoundedZoomAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/ColorIcon.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/ColorIcon.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -34,21 +34,26 @@
  */
 public class ColorIcon implements Icon {
 
-    private Color color;
+    private final Color color;
 
     public ColorIcon(Color c) {
         color = c;
     }
 
+    @Override
     public void paintIcon(Component c, Graphics g, int x, int y) {
+        Color oldColor = g.getColor();
         g.setColor(color);
         g.fillRect(x, y, 16, 16);
+        g.setColor(oldColor);
     }
 
+    @Override
     public int getIconWidth() {
         return 16;
     }
 
+    @Override
     public int getIconHeight() {
         return 16;
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/ContextAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/ContextAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2007, 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,11 +25,7 @@
 package com.sun.hotspot.igv.util;
 
 import java.awt.EventQueue;
-import org.openide.util.ContextAwareAction;
-import org.openide.util.Lookup;
-import org.openide.util.LookupEvent;
-import org.openide.util.LookupListener;
-import org.openide.util.Utilities;
+import org.openide.util.*;
 import org.openide.util.actions.CallableSystemAction;
 
 /**
@@ -56,6 +52,7 @@
         resultChanged(null);
     }
 
+    @Override
     public void resultChanged(LookupEvent e) {
         if (result.allItems().size() != 0) {
             update(result.allInstances().iterator().next());
@@ -71,6 +68,7 @@
         // Ensure it's AWT event thread
         EventQueue.invokeLater(new Runnable() {
 
+            @Override
             public void run() {
                 performAction(t);
             }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/DoubleClickAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/DoubleClickAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/DoubleClickHandler.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/DoubleClickHandler.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/ExtendedSatelliteComponent.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/ExtendedSatelliteComponent.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,11 +23,10 @@
  */
 package com.sun.hotspot.igv.util;
 
-import org.netbeans.api.visual.widget.Scene;
-
-import javax.swing.*;
 import java.awt.*;
 import java.awt.event.*;
+import javax.swing.JComponent;
+import org.netbeans.api.visual.widget.Scene;
 
 /**
  * @author David Kaspar
@@ -118,27 +117,34 @@
         }
     }
 
+    @Override
     public void mouseClicked(MouseEvent e) {
     }
 
+    @Override
     public void mousePressed(MouseEvent e) {
         moveVisibleRect(e.getPoint());
     }
 
+    @Override
     public void mouseReleased(MouseEvent e) {
         moveVisibleRect(e.getPoint());
     }
 
+    @Override
     public void mouseEntered(MouseEvent e) {
     }
 
+    @Override
     public void mouseExited(MouseEvent e) {
     }
 
+    @Override
     public void mouseDragged(MouseEvent e) {
         moveVisibleRect(e.getPoint());
     }
 
+    @Override
     public void mouseMoved(MouseEvent e) {
     }
 
@@ -170,26 +176,33 @@
 
     }
 
+    @Override
     public void sceneRepaint() {
     }
 
+    @Override
     public void sceneValidating() {
     }
 
+    @Override
     public void sceneValidated() {
     }
 
+    @Override
     public void componentResized(ComponentEvent e) {
         repaint();
     }
 
+    @Override
     public void componentMoved(ComponentEvent e) {
         repaint();
     }
 
+    @Override
     public void componentShown(ComponentEvent e) {
     }
 
+    @Override
     public void componentHidden(ComponentEvent e) {
     }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/ExtendedSelectAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/ExtendedSelectAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/LookupHistory.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,79 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+package com.sun.hotspot.igv.util;
+
+import java.util.HashMap;
+import java.util.Map;
+import org.openide.util.Lookup.Result;
+import org.openide.util.LookupEvent;
+import org.openide.util.LookupListener;
+import org.openide.util.Utilities;
+
+/**
+ *
+ * @author Thomas
+ */
+public class LookupHistory {
+
+    private static Map<Class, LookupHistoryImpl> cache = new HashMap<>();
+
+    private static class LookupHistoryImpl<T> implements LookupListener {
+
+        private Class<T> klass;
+        private Result<T> result;
+        private T last;
+
+        public LookupHistoryImpl(Class<T> klass) {
+            this.klass = klass;
+            result = Utilities.actionsGlobalContext().lookupResult(klass);
+            result.addLookupListener(this);
+            last = Utilities.actionsGlobalContext().lookup(klass);
+        }
+
+        public T getLast() {
+            return last;
+        }
+
+        @Override
+        public void resultChanged(LookupEvent ev) {
+            T current = Utilities.actionsGlobalContext().lookup(klass);
+            if (current != null) {
+                last = current;
+            }
+        }
+    }
+
+    public static <T> void init(Class<T> klass) {
+        if (!cache.containsKey(klass)) {
+            cache.put(klass, new LookupHistoryImpl<>(klass));
+        }
+    }
+
+    @SuppressWarnings("unchecked")
+    public static <T> T getLast(Class<T> klass) {
+        init(klass);
+        assert cache.containsKey(klass);
+        return (T) cache.get(klass).getLast();
+    }
+}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/PropertiesSheet.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/PropertiesSheet.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2008, 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
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/RangeSlider.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/RangeSlider.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2007, 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,33 +25,27 @@
 package com.sun.hotspot.igv.util;
 
 import com.sun.hotspot.igv.data.ChangedListener;
-import java.awt.Color;
-import java.awt.Cursor;
-import java.awt.Dimension;
-import java.awt.FontMetrics;
-import java.awt.Graphics;
-import java.awt.Graphics2D;
-import java.awt.Point;
-import java.awt.Rectangle;
-import java.awt.RenderingHints;
+import java.awt.*;
+import java.awt.geom.*;
 import java.awt.event.MouseEvent;
 import java.awt.event.MouseListener;
 import java.awt.event.MouseMotionListener;
 import java.util.List;
-import javax.swing.JComponent;
+import javax.swing.*;
 
 /**
  *
  * @author Thomas Wuerthinger
  */
-public class RangeSlider extends JComponent implements ChangedListener<RangeSliderModel>, MouseListener, MouseMotionListener {
+public class RangeSlider extends JComponent implements ChangedListener<RangeSliderModel>, MouseListener, MouseMotionListener, Scrollable {
 
     public static final int HEIGHT = 40;
-    public static final int BAR_HEIGHT = 22;
-    public static final int BAR_SELECTION_ENDING_HEIGHT = 16;
-    public static final int BAR_SELECTION_HEIGHT = 10;
-    public static final int BAR_THICKNESS = 2;
-    public static final int BAR_CIRCLE_SIZE = 9;
+    public static final float BAR_HEIGHT = 22;
+    public static final float BAR_SELECTION_ENDING_HEIGHT = 16;
+    public static final float BAR_SELECTION_HEIGHT = 10;
+    public static final float BAR_THICKNESS = 2;
+    public static final float BAR_CIRCLE_SIZE = 9;
+    public static final float BAR_CIRCLE_CONNECTOR_SIZE = 6;
     public static final int MOUSE_ENDING_OFFSET = 3;
     public static final Color BACKGROUND_COLOR = Color.white;
     public static final Color BAR_COLOR = Color.black;
@@ -98,14 +92,61 @@
         return model;
     }
 
+    /**
+     * Returns the preferred size of the viewport for a view component.
+     * For example, the preferred size of a <code>JList</code> component
+     * is the size required to accommodate all of the cells in its list.
+     * However, the value of <code>preferredScrollableViewportSize</code>
+     * is the size required for <code>JList.getVisibleRowCount</code> rows.
+     * A component without any properties that would affect the viewport
+     * size should just return <code>getPreferredSize</code> here.
+     *
+     * @return the preferredSize of a <code>JViewport</code> whose view
+     *    is this <code>Scrollable</code>
+     * @see JViewport#getPreferredSize
+     */
+    public Dimension getPreferredScrollableViewportSize() {
+        return getPreferredSize();
+    }
+
+    public int getScrollableUnitIncrement(Rectangle visibleRect, int orientation, int direction) {
+        if (orientation == SwingConstants.VERTICAL) {
+            return 1;
+        }
+
+        return (int)(BAR_CIRCLE_SIZE + BAR_CIRCLE_CONNECTOR_SIZE);
+    }
+
+    public int getScrollableBlockIncrement(Rectangle visibleRect, int orientation, int direction) {
+        return orientation == SwingConstants.VERTICAL ? visibleRect.height / 2 : visibleRect.width / 2;
+    }
+
+    public boolean getScrollableTracksViewportWidth() {
+        return false;
+    }
+
+    public boolean getScrollableTracksViewportHeight() {
+        return true;
+    }
+
     @Override
     public Dimension getPreferredSize() {
         Dimension d = super.getPreferredSize();
         d.height = HEIGHT;
+        d.width = Math.max(d.width, (int)(2 * BAR_CIRCLE_CONNECTOR_SIZE + getPaintingModel().getPositions().size() * (BAR_CIRCLE_SIZE + BAR_CIRCLE_CONNECTOR_SIZE)));
         return d;
     }
 
+    @Override
     public void changed(RangeSliderModel source) {
+        revalidate();
+
+        float barStartY = getBarStartY();
+        int circleCenterY = (int)(barStartY + BAR_HEIGHT / 2);
+        int startX = (int)getStartXPosition(model.getFirstPosition());
+        int endX = (int)getEndXPosition(model.getSecondPosition());
+        Rectangle r = new Rectangle(startX, circleCenterY, endX - startX, 1);
+        scrollRectToVisible(r);
         update();
     }
 
@@ -113,22 +154,22 @@
         this.repaint();
     }
 
-    private int getXPosition(int index) {
+    private float getXPosition(int index) {
         assert index >= 0 && index < getPaintingModel().getPositions().size();
         return getXOffset() * (index + 1);
     }
 
-    private int getXOffset() {
+    private float getXOffset() {
         int size = getPaintingModel().getPositions().size();
-        int width = getWidth();
+        float width = (float)getWidth();
         return (width / (size + 1));
     }
 
-    private int getEndXPosition(int index) {
+    private float getEndXPosition(int index) {
         return getXPosition(index) + getXOffset() / 2;
     }
 
-    private int getStartXPosition(int index) {
+    private float getStartXPosition(int index) {
         return getXPosition(index) - getXOffset() / 2;
     }
 
@@ -142,7 +183,7 @@
         int height = getHeight();
 
         g2.setColor(BACKGROUND_COLOR);
-        g2.fillRect(0, 0, width, height);
+        g2.fill(new Rectangle2D.Float(0, 0, width, height));
 
         // Nothing to paint?
         if (getPaintingModel() == null || getPaintingModel().getPositions().size() == 0) {
@@ -157,30 +198,30 @@
 
     }
 
-    private int getBarStartY() {
-        return getHeight() - BAR_HEIGHT;
+    private float getBarStartY() {
+        return getHeight() / 2 - BAR_HEIGHT / 2;
     }
 
     private void paintBar(Graphics2D g) {
         List<String> list = getPaintingModel().getPositions();
-        int barStartY = getBarStartY();
+        float barStartY = getBarStartY();
 
         g.setColor(BAR_COLOR);
-        g.fillRect(getXPosition(0), barStartY + BAR_HEIGHT / 2 - BAR_THICKNESS / 2, getXPosition(list.size() - 1) - getXPosition(0), BAR_THICKNESS);
+        g.fill(new Rectangle2D.Float(getXPosition(0), barStartY + BAR_HEIGHT / 2 - BAR_THICKNESS / 2, getXPosition(list.size() - 1) - getXPosition(0), BAR_THICKNESS));
 
-        int circleCenterY = barStartY + BAR_HEIGHT / 2;
+        float circleCenterY = barStartY + BAR_HEIGHT / 2;
         for (int i = 0; i < list.size(); i++) {
-            int curX = getXPosition(i);
+            float curX = getXPosition(i);
             g.setColor(getPaintingModel().getColors().get(i));
-            g.fillOval(curX - BAR_CIRCLE_SIZE / 2, circleCenterY - BAR_CIRCLE_SIZE / 2, BAR_CIRCLE_SIZE, BAR_CIRCLE_SIZE);
+            g.fill(new Ellipse2D.Float(curX - BAR_CIRCLE_SIZE / 2, circleCenterY - BAR_CIRCLE_SIZE / 2, BAR_CIRCLE_SIZE, BAR_CIRCLE_SIZE));
             g.setColor(Color.black);
-            g.drawOval(curX - BAR_CIRCLE_SIZE / 2, circleCenterY - BAR_CIRCLE_SIZE / 2, BAR_CIRCLE_SIZE, BAR_CIRCLE_SIZE);
+            g.draw(new Ellipse2D.Float(curX - BAR_CIRCLE_SIZE / 2, circleCenterY - BAR_CIRCLE_SIZE / 2, BAR_CIRCLE_SIZE, BAR_CIRCLE_SIZE));
 
 
             String curS = list.get(i);
             if (curS != null && curS.length() > 0) {
-                int startX = getStartXPosition(i);
-                int endX = getEndXPosition(i);
+                float startX = getStartXPosition(i);
+                float endX = getEndXPosition(i);
                 FontMetrics metrics = g.getFontMetrics();
                 Rectangle bounds = metrics.getStringBounds(curS, g).getBounds();
                 if (bounds.width < endX - startX && bounds.height < barStartY) {
@@ -194,10 +235,10 @@
 
     private void paintSelected(Graphics2D g, int start, int end) {
 
-        int startX = getStartXPosition(start);
-        int endX = getEndXPosition(end);
-        int barStartY = getBarStartY();
-        int barSelectionEndingStartY = barStartY + BAR_HEIGHT / 2 - BAR_SELECTION_ENDING_HEIGHT / 2;
+        float startX = getStartXPosition(start);
+        float endX = getEndXPosition(end);
+        float barStartY = getBarStartY();
+        float barSelectionEndingStartY = barStartY + BAR_HEIGHT / 2 - BAR_SELECTION_ENDING_HEIGHT / 2;
         paintSelectedEnding(g, startX, barSelectionEndingStartY);
         paintSelectedEnding(g, endX, barSelectionEndingStartY);
 
@@ -207,18 +248,18 @@
         } else if (isOverBar) {
             g.setColor(BAR_SELECTION_COLOR_ROLLOVER);
         }
-        g.fillRect(startX, barStartY + BAR_HEIGHT / 2 - BAR_SELECTION_HEIGHT / 2, endX - startX, BAR_SELECTION_HEIGHT);
+        g.fill(new Rectangle2D.Float(startX, barStartY + BAR_HEIGHT / 2 - BAR_SELECTION_HEIGHT / 2, endX - startX, BAR_SELECTION_HEIGHT));
     }
 
-    private void paintSelectedEnding(Graphics g, int x, int y) {
+    private void paintSelectedEnding(Graphics2D g, float x, float y) {
         g.setColor(BAR_COLOR);
-        g.fillRect(x - BAR_THICKNESS / 2, y, BAR_THICKNESS, BAR_SELECTION_ENDING_HEIGHT);
+        g.fill(new Rectangle2D.Float(x - BAR_THICKNESS / 2, y, BAR_THICKNESS, BAR_SELECTION_ENDING_HEIGHT));
     }
 
     private boolean isOverSecondPosition(Point p) {
         if (p.y >= getBarStartY()) {
-            int destX = getEndXPosition(getPaintingModel().getSecondPosition());
-            int off = Math.abs(destX - p.x);
+            float destX = getEndXPosition(getPaintingModel().getSecondPosition());
+            float off = Math.abs(destX - p.x);
             return off <= MOUSE_ENDING_OFFSET;
         }
         return false;
@@ -226,8 +267,8 @@
 
     private boolean isOverFirstPosition(Point p) {
         if (p.y >= getBarStartY()) {
-            int destX = getStartXPosition(getPaintingModel().getFirstPosition());
-            int off = Math.abs(destX - p.x);
+            float destX = getStartXPosition(getPaintingModel().getFirstPosition());
+            float off = Math.abs(destX - p.x);
             return off <= MOUSE_ENDING_OFFSET;
         }
         return false;
@@ -240,10 +281,14 @@
         return false;
     }
 
+    @Override
     public void mouseDragged(MouseEvent e) {
+        Rectangle r = new Rectangle(e.getX(), e.getY(), 1, 1);
+        scrollRectToVisible(r);
+
         if (state == State.DragBar) {
-            int firstX = this.getStartXPosition(model.getFirstPosition());
-            int newFirstX = firstX + e.getPoint().x - startPoint.x;
+            float firstX = this.getStartXPosition(model.getFirstPosition());
+            float newFirstX = firstX + e.getPoint().x - startPoint.x;
             int newIndex = getIndexFromPosition(newFirstX) + 1;
             if (newIndex + model.getSecondPosition() - model.getFirstPosition() >= model.getPositions().size()) {
                 newIndex = model.getPositions().size() - (model.getSecondPosition() - model.getFirstPosition()) - 1;
@@ -270,13 +315,13 @@
         }
     }
 
-    private int getIndexFromPosition(int x) {
+    private int getIndexFromPosition(float x) {
         if (x < getXPosition(0)) {
             return -1;
         }
         for (int i = 0; i < getPaintingModel().getPositions().size() - 1; i++) {
-            int startX = getXPosition(i);
-            int endX = getXPosition(i + 1);
+            float startX = getXPosition(i);
+            float endX = getXPosition(i + 1);
             if (x >= startX && x <= endX) {
                 return i;
             }
@@ -286,7 +331,7 @@
 
     private int getCircleIndexFromPosition(int x) {
         int result = 0;
-        for (int i = 1; i < getPaintingModel().getPositions().size() - 1; i++) {
+        for (int i = 1; i < getPaintingModel().getPositions().size(); i++) {
             if (x > getStartXPosition(i)) {
                 result = i;
             }
@@ -294,6 +339,7 @@
         return result;
     }
 
+    @Override
     public void mouseMoved(MouseEvent e) {
         isOverBar = false;
         if (model == null) {
@@ -313,6 +359,7 @@
         repaint();
     }
 
+    @Override
     public void mouseClicked(MouseEvent e) {
         if (e.getClickCount() > 1) {
             // Double click
@@ -321,6 +368,7 @@
         }
     }
 
+    @Override
     public void mousePressed(MouseEvent e) {
         if (model == null) {
             return;
@@ -341,6 +389,7 @@
         tempModel = model.copy();
     }
 
+    @Override
     public void mouseReleased(MouseEvent e) {
         if (model == null || tempModel == null) {
             return;
@@ -350,9 +399,11 @@
         tempModel = null;
     }
 
+    @Override
     public void mouseEntered(MouseEvent e) {
     }
 
+    @Override
     public void mouseExited(MouseEvent e) {
         isOverBar = false;
         repaint();
--- a/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/RangeSliderModel.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/Util/src/com/sun/hotspot/igv/util/RangeSliderModel.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2008, 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
@@ -24,8 +24,8 @@
  */
 package com.sun.hotspot.igv.util;
 
+import com.sun.hotspot.igv.data.ChangedEvent;
 import com.sun.hotspot.igv.data.ChangedEventProvider;
-import com.sun.hotspot.igv.data.ChangedEvent;
 import java.awt.Color;
 import java.util.ArrayList;
 import java.util.Collections;
@@ -65,17 +65,19 @@
 
     public RangeSliderModel(List<String> positions) {
         assert positions.size() > 0;
-        this.changedEvent = new ChangedEvent<RangeSliderModel>(this);
-        this.colorChangedEvent = new ChangedEvent<RangeSliderModel>(this);
+        this.changedEvent = new ChangedEvent<>(this);
+        this.colorChangedEvent = new ChangedEvent<>(this);
         setPositions(positions);
     }
 
     protected void setPositions(List<String> positions) {
         this.positions = positions;
-        colors = new ArrayList<Color>();
+        colors = new ArrayList<>();
         for (int i = 0; i < positions.size(); i++) {
             colors.add(Color.black);
         }
+        firstPosition = Math.min(firstPosition, positions.size() - 1);
+        secondPosition = Math.min(secondPosition, positions.size() - 1);
         changedEvent.fire();
         colorChangedEvent.fire();
     }
@@ -91,9 +93,7 @@
 
     public RangeSliderModel copy() {
         RangeSliderModel newModel = new RangeSliderModel(positions);
-        newModel.firstPosition = firstPosition;
-        newModel.secondPosition = secondPosition;
-        newModel.colors = colors;
+        newModel.setData(this);
         return newModel;
     }
 
@@ -130,6 +130,7 @@
         return colorChangedEvent;
     }
 
+    @Override
     public ChangedEvent<RangeSliderModel> getChangedEvent() {
         return changedEvent;
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/nbproject/project.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/nbproject/project.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,2 +1,2 @@
-javac.source=1.5
-javac.compilerargs=-Xlint -Xlint:-serial
+javac.source=1.7
+javac.compilerargs=-Xlint -Xlint:-serial
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/nbproject/project.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/nbproject/project.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -55,6 +55,14 @@
                     </run-dependency>
                 </dependency>
                 <dependency>
+                    <code-name-base>com.sun.hotspot.igv.selectioncoordinator</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>1.0</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
                     <code-name-base>com.sun.hotspot.igv.settings</code-name-base>
                     <build-prerequisite/>
                     <compile-dependency/>
@@ -83,7 +91,15 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>2.9</specification-version>
+                        <specification-version>2.27.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.netbeans.spi.quicksearch</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>1.0</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -91,7 +107,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>6.6.0.1</specification-version>
+                        <specification-version>6.21.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -99,7 +115,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>6.11.0.1</specification-version>
+                        <specification-version>7.30.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -107,7 +123,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>7.5.1</specification-version>
+                        <specification-version>7.18.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -115,7 +131,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>6.7</specification-version>
+                        <specification-version>7.20.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -123,7 +139,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>7.2.1.1</specification-version>
+                        <specification-version>7.20.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -131,7 +147,15 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>7.9.0.1</specification-version>
+                        <specification-version>8.14.1</specification-version>
+                    </run-dependency>
+                </dependency>
+                <dependency>
+                    <code-name-base>org.openide.util.lookup</code-name-base>
+                    <build-prerequisite/>
+                    <compile-dependency/>
+                    <run-dependency>
+                        <specification-version>8.6.1</specification-version>
                     </run-dependency>
                 </dependency>
                 <dependency>
@@ -139,7 +163,7 @@
                     <build-prerequisite/>
                     <compile-dependency/>
                     <run-dependency>
-                        <specification-version>6.16</specification-version>
+                        <specification-version>6.39.1</specification-version>
                     </run-dependency>
                 </dependency>
             </module-dependencies>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/META-INF/services/com.sun.hotspot.igv.data.services.InputGraphProvider	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,1 +0,0 @@
-com.sun.hotspot.igv.view.EditorInputGraphProvider
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/BoundedZoomAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/BoundedZoomAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/Bundle.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/Bundle.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,3 +1,3 @@
-HINT_EditorTopComponent=This is a Editor window
-OpenIDE-Module-Name=View
-CTL_EditorTopComponent=Editor Window
+HINT_EditorTopComponent=Visualizes a graph.
+OpenIDE-Module-Name=View
+CTL_EditorTopComponent=Graph
\ No newline at end of file
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/ConnectionAnchor.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,84 +0,0 @@
-/*
- * Copyright (c) 2008, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- *
- */
-package com.sun.hotspot.igv.view;
-
-import com.sun.hotspot.igv.view.widgets.SlotWidget;
-import java.awt.Point;
-import java.awt.Rectangle;
-import org.netbeans.api.visual.anchor.Anchor;
-import org.netbeans.api.visual.anchor.Anchor.Entry;
-import org.netbeans.api.visual.anchor.Anchor.Result;
-import org.netbeans.api.visual.widget.Widget;
-
-/**
- *
- * @author Thomas Wuerthinger
- */
-public class ConnectionAnchor extends Anchor {
-
-    public enum HorizontalAlignment {
-
-        Left,
-        Center,
-        Right
-    }
-    private HorizontalAlignment alignment;
-
-    public ConnectionAnchor(Widget widget) {
-        this(HorizontalAlignment.Center, widget);
-    }
-
-    public ConnectionAnchor(HorizontalAlignment alignment, Widget widget) {
-        super(widget);
-        this.alignment = alignment;
-    }
-
-    public Result compute(Entry entry) {
-        return new Result(getRelatedSceneLocation(), Anchor.DIRECTION_ANY);
-    }
-
-    @Override
-    public Point getRelatedSceneLocation() {
-        Point p = null;
-        Widget w = getRelatedWidget();
-        if (w != null) {
-            if (w instanceof SlotWidget) {
-                p = ((SlotWidget) w).getAnchorPosition();
-            } else {
-                Rectangle r = w.convertLocalToScene(w.getBounds());
-                int y = r.y + r.height / 2;
-                int x = r.x;
-                if (alignment == HorizontalAlignment.Center) {
-                    x = r.x + r.width / 2;
-                } else if (alignment == HorizontalAlignment.Right) {
-                    x = r.x + r.width;
-                }
-
-                p = new Point(x, y);
-            }
-        }
-
-        return p;
-    }
-}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/DiagramScene.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/DiagramScene.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,77 +23,42 @@
  */
 package com.sun.hotspot.igv.view;
 
-import com.sun.hotspot.igv.view.widgets.BlockWidget;
-import com.sun.hotspot.igv.view.widgets.LineWidget;
-import com.sun.hotspot.igv.util.DoubleClickAction;
+import com.sun.hotspot.igv.data.ChangedListener;
+import com.sun.hotspot.igv.data.ControllableChangedListener;
 import com.sun.hotspot.igv.data.InputBlock;
 import com.sun.hotspot.igv.data.InputNode;
-import com.sun.hotspot.igv.graph.Connection;
-import com.sun.hotspot.igv.graph.Diagram;
-import com.sun.hotspot.igv.graph.Figure;
-import com.sun.hotspot.igv.graph.InputSlot;
-import com.sun.hotspot.igv.graph.OutputSlot;
-import com.sun.hotspot.igv.graph.Slot;
+import com.sun.hotspot.igv.data.Pair;
+import com.sun.hotspot.igv.data.Properties;
+import com.sun.hotspot.igv.data.services.Scheduler;
+import com.sun.hotspot.igv.graph.*;
 import com.sun.hotspot.igv.hierarchicallayout.HierarchicalClusterLayoutManager;
-import com.sun.hotspot.igv.hierarchicallayout.OldHierarchicalLayoutManager;
 import com.sun.hotspot.igv.hierarchicallayout.HierarchicalLayoutManager;
-import com.sun.hotspot.igv.view.widgets.FigureWidget;
-import com.sun.hotspot.igv.view.widgets.InputSlotWidget;
-import com.sun.hotspot.igv.view.widgets.OutputSlotWidget;
-import com.sun.hotspot.igv.view.widgets.SlotWidget;
 import com.sun.hotspot.igv.layout.LayoutGraph;
-import com.sun.hotspot.igv.data.services.Scheduler;
-import com.sun.hotspot.igv.data.ChangedListener;
-import com.sun.hotspot.igv.graph.Block;
+import com.sun.hotspot.igv.selectioncoordinator.SelectionCoordinator;
 import com.sun.hotspot.igv.util.ColorIcon;
-import com.sun.hotspot.igv.util.ExtendedSelectAction;
-import java.awt.Color;
-import java.awt.Dimension;
-import java.awt.Point;
-import java.awt.Rectangle;
-import java.awt.event.ActionEvent;
-import java.awt.event.FocusEvent;
-import java.awt.event.FocusListener;
-import java.awt.event.MouseEvent;
-import java.awt.event.MouseListener;
-import java.awt.event.MouseMotionListener;
-import java.awt.event.MouseWheelEvent;
-import java.awt.event.MouseWheelListener;
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.HashMap;
+import com.sun.hotspot.igv.util.DoubleClickAction;
+import com.sun.hotspot.igv.util.PropertiesSheet;
+import com.sun.hotspot.igv.view.actions.CustomizablePanAction;
+import com.sun.hotspot.igv.view.widgets.*;
+import java.awt.*;
+import java.awt.event.*;
 import java.util.List;
-import java.util.Map;
-import java.util.Set;
-import javax.swing.AbstractAction;
-import javax.swing.Action;
-import javax.swing.BorderFactory;
-import javax.swing.JComponent;
-import javax.swing.JPopupMenu;
-import javax.swing.JScrollPane;
-import javax.swing.SwingUtilities;
-import javax.swing.event.ChangeEvent;
-import javax.swing.event.ChangeListener;
+import java.util.*;
+import javax.swing.*;
 import javax.swing.event.UndoableEditEvent;
 import javax.swing.undo.AbstractUndoableEdit;
 import javax.swing.undo.CannotRedoException;
 import javax.swing.undo.CannotUndoException;
-import org.netbeans.api.visual.action.ActionFactory;
-import org.netbeans.api.visual.action.PopupMenuProvider;
-import org.netbeans.api.visual.action.RectangularSelectDecorator;
-import org.netbeans.api.visual.action.RectangularSelectProvider;
-import org.netbeans.api.visual.action.SelectProvider;
-import org.netbeans.api.visual.action.WidgetAction;
+import org.netbeans.api.visual.action.*;
 import org.netbeans.api.visual.animator.SceneAnimator;
 import org.netbeans.api.visual.layout.LayoutFactory;
-import org.netbeans.api.visual.widget.ConnectionWidget;
+import org.netbeans.api.visual.model.*;
 import org.netbeans.api.visual.widget.LayerWidget;
-import org.netbeans.api.visual.widget.Scene;
 import org.netbeans.api.visual.widget.Widget;
-import org.netbeans.api.visual.widget.LabelWidget;
 import org.openide.awt.UndoRedo;
+import org.openide.nodes.AbstractNode;
+import org.openide.nodes.Children;
+import org.openide.nodes.Sheet;
 import org.openide.util.Lookup;
 import org.openide.util.lookup.AbstractLookup;
 import org.openide.util.lookup.InstanceContent;
@@ -102,54 +67,58 @@
  *
  * @author Thomas Wuerthinger
  */
-public class DiagramScene extends Scene implements ChangedListener<DiagramViewModel> {
+public class DiagramScene extends ObjectScene implements DiagramViewer {
 
-    private HashMap<Figure, FigureWidget> figureWidgets;
-    private HashMap<Slot, SlotWidget> slotWidgets;
-    private HashMap<Connection, ConnectionWidget> connectionWidgets;
-    private HashMap<InputBlock, BlockWidget> blockWidgets;
-    private Widget hoverWidget;
+    private CustomizablePanAction panAction;
     private WidgetAction hoverAction;
-    private List<FigureWidget> selectedWidgets;
+    private WidgetAction selectAction;
     private Lookup lookup;
     private InstanceContent content;
     private Action[] actions;
+    private Action[] actionsWithSelection;
     private LayerWidget connectionLayer;
     private JScrollPane scrollPane;
     private UndoRedo.Manager undoRedoManager;
     private LayerWidget mainLayer;
-    private LayerWidget slotLayer;
     private LayerWidget blockLayer;
-    private double realZoomFactor;
-    private BoundedZoomAction zoomAction;
-    private WidgetAction panAction;
     private Widget topLeft;
     private Widget bottomRight;
-    private LayerWidget startLayer;
-    private LabelWidget startLabel;
     private DiagramViewModel model;
     private DiagramViewModel modelCopy;
-    public static final int AFTER = 1;
-    public static final int BEFORE = 1;
+    private WidgetAction zoomAction;
+    private boolean rebuilding;
+
+    /**
+     * The alpha level of partially visible figures.
+     */
     public static final float ALPHA = 0.4f;
-    public static final int GRID_SIZE = 30;
+
+    /**
+     * The offset of the graph to the border of the window showing it.
+     */
     public static final int BORDER_SIZE = 20;
+
+
     public static final int UNDOREDO_LIMIT = 100;
     public static final int SCROLL_UNIT_INCREMENT = 80;
     public static final int SCROLL_BLOCK_INCREMENT = 400;
     public static final float ZOOM_MAX_FACTOR = 3.0f;
     public static final float ZOOM_MIN_FACTOR = 0.0f;//0.15f;
     public static final float ZOOM_INCREMENT = 1.5f;
-    public static final int SLOT_OFFSET = 6;
+    public static final int SLOT_OFFSET = 8;
     public static final int ANIMATION_LIMIT = 40;
+
     private PopupMenuProvider popupMenuProvider = new PopupMenuProvider() {
 
+        @Override
         public JPopupMenu getPopupMenu(Widget widget, Point localLocation) {
             return DiagramScene.this.createPopupMenu();
         }
     };
+
     private RectangularSelectDecorator rectangularSelectDecorator = new RectangularSelectDecorator() {
 
+        @Override
         public Widget createSelectionWidget() {
             Widget widget = new Widget(DiagramScene.this);
             widget.setBorder(BorderFactory.createLineBorder(Color.black, 2));
@@ -157,8 +126,98 @@
             return widget;
         }
     };
+
+    @SuppressWarnings("unchecked")
+    public <T> T getWidget(Object o) {
+        Widget w = this.findWidget(o);
+        return (T) w;
+    }
+
+    @SuppressWarnings("unchecked")
+    public <T> T getWidget(Object o, Class<T> klass) {
+        Widget w = this.findWidget(o);
+        return (T) w;
+    }
+
+    private static boolean intersects(Set<? extends Object> s1, Set<? extends Object> s2) {
+        for (Object o : s1) {
+            if (s2.contains(o)) {
+                return true;
+            }
+        }
+        return false;
+    }
+
+    @Override
+    public void zoomOut() {
+        double zoom = getZoomFactor();
+        Point viewPosition = getScrollPane().getViewport().getViewPosition();
+        double newZoom = zoom / DiagramScene.ZOOM_INCREMENT;
+        if (newZoom > DiagramScene.ZOOM_MIN_FACTOR) {
+            setZoomFactor(newZoom);
+            validate();
+            getScrollPane().getViewport().setViewPosition(new Point((int) (viewPosition.x / DiagramScene.ZOOM_INCREMENT), (int) (viewPosition.y / DiagramScene.ZOOM_INCREMENT)));
+        }
+    }
+
+    @Override
+    public void zoomIn() {
+
+        double zoom = getZoomFactor();
+        Point viewPosition = getScrollPane().getViewport().getViewPosition();
+        double newZoom = zoom * DiagramScene.ZOOM_INCREMENT;
+        if (newZoom < DiagramScene.ZOOM_MAX_FACTOR) {
+            setZoomFactor(newZoom);
+            validate();
+            getScrollPane().getViewport().setViewPosition(new Point((int) (viewPosition.x * DiagramScene.ZOOM_INCREMENT), (int) (viewPosition.y * DiagramScene.ZOOM_INCREMENT)));
+        }
+    }
+
+
+    @Override
+    public void centerFigures(List<Figure> list) {
+
+        boolean b = getUndoRedoEnabled();
+        setUndoRedoEnabled(false);
+        gotoFigures(list);
+        setUndoRedoEnabled(b);
+    }
+
+    private Set<Object> getObjectsFromIdSet(Set<Object> set) {
+        Set<Object> selectedObjects = new HashSet<>();
+        for (Figure f : getModel().getDiagramToView().getFigures()) {
+            if (intersects(f.getSource().getSourceNodesAsSet(), set)) {
+                selectedObjects.add(f);
+            }
+
+            for (Slot s : f.getSlots()) {
+                if (intersects(s.getSource().getSourceNodesAsSet(), set)) {
+                    selectedObjects.add(s);
+                }
+            }
+        }
+        return selectedObjects;
+    }
+    private ControllableChangedListener<SelectionCoordinator> highlightedCoordinatorListener = new ControllableChangedListener<SelectionCoordinator>() {
+
+        @Override
+        public void filteredChanged(SelectionCoordinator source) {
+            DiagramScene.this.setHighlightedObjects(getObjectsFromIdSet(source.getHighlightedObjects()));
+            DiagramScene.this.validate();
+        }
+    };
+    private ControllableChangedListener<SelectionCoordinator> selectedCoordinatorListener = new ControllableChangedListener<SelectionCoordinator>() {
+
+        @Override
+        public void filteredChanged(SelectionCoordinator source) {
+            DiagramScene.this.gotoSelection(source.getSelectedObjects());
+            DiagramScene.this.validate();
+        }
+    };
+
     private RectangularSelectProvider rectangularSelectProvider = new RectangularSelectProvider() {
 
+        @Override
         public void performSelection(Rectangle rectangle) {
             if (rectangle.width < 0) {
                 rectangle.x += rectangle.width;
@@ -170,168 +229,44 @@
                 rectangle.height *= -1;
             }
 
-            boolean updated = false;
+            Set<Object> selectedObjects = new HashSet<>();
             for (Figure f : getModel().getDiagramToView().getFigures()) {
-                FigureWidget w = figureWidgets.get(f);
-                Rectangle r = new Rectangle(w.getBounds());
-                r.setLocation(w.getLocation());
-                if (r.intersects(rectangle)) {
-                    if (!selectedWidgets.contains(w)) {
-                        addToSelection(w);
-                        updated = true;
+                FigureWidget w = getWidget(f);
+                if (w != null) {
+                    Rectangle r = new Rectangle(w.getBounds());
+                    r.setLocation(w.getLocation());
+
+                    if (r.intersects(rectangle)) {
+                        selectedObjects.add(f);
+                    }
+
+                    for (Slot s : f.getSlots()) {
+                        SlotWidget sw = getWidget(s);
+                        Rectangle r2 = new Rectangle(sw.getBounds());
+                        r2.setLocation(sw.convertLocalToScene(new Point(0, 0)));
+
+                        if (r2.intersects(rectangle)) {
+                            selectedObjects.add(s);
+                        }
                     }
                 } else {
-                    if (selectedWidgets.contains(w)) {
-                        selectedWidgets.remove(w);
-                        content.remove(w.getNode());
-                        w.setState(w.getState().deriveSelected(false));
-                        updated = true;
-                    }
-                }
-            }
-
-            if (updated) {
-                selectionUpdated();
-            }
-        }
-    };
-    private SelectProvider selectProvider = new SelectProvider() {
-
-        public boolean isAimingAllowed(Widget widget, Point point, boolean b) {
-            return false;
-        }
-
-        public boolean isSelectionAllowed(Widget widget, Point point, boolean b) {
-            return widget instanceof FigureWidget || widget == DiagramScene.this;
-        }
-
-        public void select(Widget w, Point point, boolean change) {
-
-            boolean updated = false;
-
-            if (w == DiagramScene.this) {
-                if (DiagramScene.this.selectedWidgets.size() != 0) {
-                    clearSelection();
-                    selectionUpdated();
-                }
-                return;
-            }
-
-            FigureWidget widget = (FigureWidget) w;
-
-
-            if (change) {
-                if (widget.getState().isSelected()) {
-                    assert selectedWidgets.contains(widget);
-                    widget.setState(widget.getState().deriveSelected(false));
-                    selectedWidgets.remove(widget);
-                    content.remove(widget.getNode());
-                    updated = true;
-                } else {
-                    assert !selectedWidgets.contains(widget);
-                    addToSelection(widget);
-                    updated = true;
-                    assert widget.getState().isSelected();
-                }
-            } else {
-
-                if (widget.getState().isSelected()) {
-                    assert selectedWidgets.contains(widget);
-                } else {
-
-                    assert !selectedWidgets.contains(widget);
-                    clearSelection();
-                    addToSelection(widget);
-                    updated = true;
-                    assert widget.getState().isSelected();
+                    assert false : "w should not be null here!";
                 }
             }
 
-            if (updated) {
-                selectionUpdated();
-            }
-
+            setSelectedObjects(selectedObjects);
         }
     };
 
-    private FigureWidget getFigureWidget(Figure f) {
-        return figureWidgets.get(f);
-    }
-    private FocusListener focusListener = new FocusListener() {
-
-        public void focusGained(FocusEvent e) {
-            DiagramScene.this.getView().requestFocus();
-        }
-
-        public void focusLost(FocusEvent e) {
-        }
-    };
     private MouseWheelListener mouseWheelListener = new MouseWheelListener() {
 
+        @Override
         public void mouseWheelMoved(MouseWheelEvent e) {
-            DiagramScene.this.zoomAction.mouseWheelMoved(DiagramScene.this, new WidgetAction.WidgetMouseWheelEvent(0, e));
-            DiagramScene.this.validate();
+            if (e.isControlDown()) {
+                DiagramScene.this.relayoutWithoutLayout(null);
+            }
         }
     };
-    private MouseListener mouseListener = new MouseListener() {
-
-        public void mouseClicked(MouseEvent e) {
-            DiagramScene.this.panAction.mouseClicked(DiagramScene.this, new WidgetAction.WidgetMouseEvent(0, e));
-        }
-
-        public void mousePressed(MouseEvent e) {
-            DiagramScene.this.panAction.mousePressed(DiagramScene.this, new WidgetAction.WidgetMouseEvent(0, e));
-        }
-
-        public void mouseReleased(MouseEvent e) {
-            DiagramScene.this.panAction.mouseReleased(DiagramScene.this, new WidgetAction.WidgetMouseEvent(0, e));
-        }
-
-        public void mouseEntered(MouseEvent e) {
-            DiagramScene.this.panAction.mouseEntered(DiagramScene.this, new WidgetAction.WidgetMouseEvent(0, e));
-        }
-
-        public void mouseExited(MouseEvent e) {
-            DiagramScene.this.panAction.mouseExited(DiagramScene.this, new WidgetAction.WidgetMouseEvent(0, e));
-        }
-    };
-    private MouseMotionListener mouseMotionListener = new MouseMotionListener() {
-
-        public void mouseDragged(MouseEvent e) {
-            DiagramScene.this.panAction.mouseDragged(DiagramScene.this, new WidgetAction.WidgetMouseEvent(0, e));
-        }
-
-        public void mouseMoved(MouseEvent e) {
-        }
-    };
-    private ScrollChangeListener scrollChangeListener = new ScrollChangeListener();
-
-    private class ScrollChangeListener implements ChangeListener {
-
-        private Map<Widget, Point> relativePositions = new HashMap<Widget, Point>();
-        private Point oldPosition;
-
-        public void register(Widget w, Point p) {
-            relativePositions.put(w, p);
-        }
-
-        public void unregister(Widget w) {
-            relativePositions.remove(w);
-        }
-
-        public void stateChanged(ChangeEvent e) {
-            Point p = DiagramScene.this.getScrollPane().getViewport().getViewPosition();
-            if (oldPosition == null || !p.equals(oldPosition)) {
-                for (Widget w : relativePositions.keySet()) {
-                    Point curPoint = relativePositions.get(w);
-                    Point newPoint = new Point(p.x + curPoint.x, p.y + curPoint.y);
-                    w.setPreferredLocation(newPoint);
-                    DiagramScene.this.validate();
-                }
-                oldPosition = p;
-            }
-        }
-    }
 
     public Point getScrollPosition() {
         return getScrollPane().getViewport().getViewPosition();
@@ -341,42 +276,138 @@
         getScrollPane().getViewport().setViewPosition(p);
     }
 
-    public DiagramScene(Action[] actions, DiagramViewModel model) {
-        this.actions = actions;
-        selectedWidgets = new ArrayList<FigureWidget>();
-        content = new InstanceContent();
-        lookup = new AbstractLookup(content);
-        this.setCheckClipping(true);
-        this.getInputBindings().setZoomActionModifiers(0);
-
+    private JScrollPane createScrollPane() {
         JComponent comp = this.createView();
         comp.setDoubleBuffered(true);
         comp.setBackground(Color.WHITE);
         comp.setOpaque(true);
-
         this.setBackground(Color.WHITE);
         this.setOpaque(true);
-        scrollPane = new JScrollPane(comp);
-        scrollPane.setBackground(Color.WHITE);
-        scrollPane.getVerticalScrollBar().setUnitIncrement(SCROLL_UNIT_INCREMENT);
-        scrollPane.getVerticalScrollBar().setBlockIncrement(SCROLL_BLOCK_INCREMENT);
-        scrollPane.getHorizontalScrollBar().setUnitIncrement(SCROLL_UNIT_INCREMENT);
-        scrollPane.getHorizontalScrollBar().setBlockIncrement(SCROLL_BLOCK_INCREMENT);
-        scrollPane.getViewport().addChangeListener(scrollChangeListener);
-        hoverAction = this.createWidgetHoverAction();
+        JScrollPane result = new JScrollPane(comp);
+        result.setBackground(Color.WHITE);
+        result.getVerticalScrollBar().setUnitIncrement(SCROLL_UNIT_INCREMENT);
+        result.getVerticalScrollBar().setBlockIncrement(SCROLL_BLOCK_INCREMENT);
+        result.getHorizontalScrollBar().setUnitIncrement(SCROLL_UNIT_INCREMENT);
+        result.getHorizontalScrollBar().setBlockIncrement(SCROLL_BLOCK_INCREMENT);
+        return result;
+    }
+    private ObjectSceneListener selectionChangedListener = new ObjectSceneListener() {
+
+        @Override
+        public void objectAdded(ObjectSceneEvent arg0, Object arg1) {
+        }
+
+        @Override
+        public void objectRemoved(ObjectSceneEvent arg0, Object arg1) {
+        }
+
+        @Override
+        public void objectStateChanged(ObjectSceneEvent e, Object o, ObjectState oldState, ObjectState newState) {
+        }
+
+        @Override
+        public void selectionChanged(ObjectSceneEvent e, Set<Object> oldSet, Set<Object> newSet) {
+            DiagramScene scene = (DiagramScene) e.getObjectScene();
+            if (scene.isRebuilding()) {
+                return;
+            }
+
+            content.set(newSet, null);
+
+            Set<Integer> nodeSelection = new HashSet<>();
+            for (Object o : newSet) {
+                if (o instanceof Properties.Provider) {
+                    final Properties.Provider provider = (Properties.Provider) o;
+                    AbstractNode node = new AbstractNode(Children.LEAF) {
+
+                        @Override
+                        protected Sheet createSheet() {
+                            Sheet s = super.createSheet();
+                            PropertiesSheet.initializeSheet(provider.getProperties(), s);
+                            return s;
+                        }
+                    };
+                    node.setDisplayName(provider.getProperties().get("name"));
+                    content.add(node);
+                }
+
+
+                if (o instanceof Figure) {
+                    nodeSelection.addAll(((Figure) o).getSource().getSourceNodesAsSet());
+                } else if (o instanceof Slot) {
+                    nodeSelection.addAll(((Slot) o).getSource().getSourceNodesAsSet());
+                }
+            }
+            getModel().setSelectedNodes(nodeSelection);
+
+            boolean b = selectedCoordinatorListener.isEnabled();
+            selectedCoordinatorListener.setEnabled(false);
+            SelectionCoordinator.getInstance().setSelectedObjects(nodeSelection);
+            selectedCoordinatorListener.setEnabled(b);
+
+        }
+
+        @Override
+        public void highlightingChanged(ObjectSceneEvent e, Set<Object> oldSet, Set<Object> newSet) {
+            Set<Integer> nodeHighlighting = new HashSet<>();
+            for (Object o : newSet) {
+                if (o instanceof Figure) {
+                    nodeHighlighting.addAll(((Figure) o).getSource().getSourceNodesAsSet());
+                } else if (o instanceof Slot) {
+                    nodeHighlighting.addAll(((Slot) o).getSource().getSourceNodesAsSet());
+                }
+            }
+            boolean b = highlightedCoordinatorListener.isEnabled();
+            highlightedCoordinatorListener.setEnabled(false);
+            SelectionCoordinator.getInstance().setHighlightedObjects(nodeHighlighting);
+            highlightedCoordinatorListener.setEnabled(true);
+        }
+
+        @Override
+        public void hoverChanged(ObjectSceneEvent e, Object oldObject, Object newObject) {
+            Set<Object> newHighlightedObjects = new HashSet<>(DiagramScene.this.getHighlightedObjects());
+            if (oldObject != null) {
+                newHighlightedObjects.remove(oldObject);
+            }
+            if (newObject != null) {
+                newHighlightedObjects.add(newObject);
+            }
+            DiagramScene.this.setHighlightedObjects(newHighlightedObjects);
+        }
+
+        @Override
+        public void focusChanged(ObjectSceneEvent arg0, Object arg1, Object arg2) {
+        }
+    };
+
+    public DiagramScene(Action[] actions, Action[] actionsWithSelection, DiagramViewModel model) {
+
+        this.actions = actions;
+        this.actionsWithSelection = actionsWithSelection;
+
+        content = new InstanceContent();
+        lookup = new AbstractLookup(content);
+
+        this.setCheckClipping(true);
+
+        scrollPane = createScrollPane();
+
+        hoverAction = createObjectHoverAction();
+
+        // This panAction handles the event only when the left mouse button is
+        // pressed without any modifier keys, otherwise it will not consume it
+        // and the selection action (below) will handle the event
+        panAction = new CustomizablePanAction(~0, MouseEvent.BUTTON1_DOWN_MASK);
+        this.getActions().addAction(panAction);
+
+        selectAction = createSelectAction();
+        this.getActions().addAction(selectAction);
 
         blockLayer = new LayerWidget(this);
         this.addChild(blockLayer);
 
-        startLayer = new LayerWidget(this);
-        this.addChild(startLayer);
-        // TODO: String startLabelString = "Loading graph with " + originalDiagram.getFigures().size() + " figures and " + originalDiagram.getConnections().size() + " connections...";
-        String startLabelString = "";
-        LabelWidget w = new LabelWidget(this, startLabelString);
-        scrollChangeListener.register(w, new Point(10, 10));
-        w.setAlignment(LabelWidget.Alignment.CENTER);
-        startLabel = w;
-        startLayer.addChild(w);
+        connectionLayer = new LayerWidget(this);
+        this.addChild(connectionLayer);
 
         mainLayer = new LayerWidget(this);
         this.addChild(mainLayer);
@@ -385,83 +416,53 @@
         topLeft.setPreferredLocation(new Point(-BORDER_SIZE, -BORDER_SIZE));
         this.addChild(topLeft);
 
-
         bottomRight = new Widget(this);
         bottomRight.setPreferredLocation(new Point(-BORDER_SIZE, -BORDER_SIZE));
         this.addChild(bottomRight);
 
-        slotLayer = new LayerWidget(this);
-        this.addChild(slotLayer);
-
-        connectionLayer = new LayerWidget(this);
-        this.addChild(connectionLayer);
-
         LayerWidget selectionLayer = new LayerWidget(this);
         this.addChild(selectionLayer);
 
         this.setLayout(LayoutFactory.createAbsoluteLayout());
 
-        this.getActions().addAction(hoverAction);
-        zoomAction = new BoundedZoomAction(1.1, false);
-        zoomAction.setMaxFactor(ZOOM_MAX_FACTOR);
-        zoomAction.setMinFactor(ZOOM_MIN_FACTOR);
-        this.getActions().addAction(ActionFactory.createMouseCenteredZoomAction(1.1));
-        panAction = new ExtendedPanAction();
-        this.getActions().addAction(panAction);
+        this.getInputBindings().setZoomActionModifiers(KeyEvent.CTRL_MASK);
+        zoomAction = ActionFactory.createMouseCenteredZoomAction(1.2);
+        this.getActions().addAction(zoomAction);
+        this.getView().addMouseWheelListener(mouseWheelListener);
         this.getActions().addAction(ActionFactory.createPopupMenuAction(popupMenuProvider));
 
+        this.getActions().addAction(ActionFactory.createWheelPanAction());
+
         LayerWidget selectLayer = new LayerWidget(this);
         this.addChild(selectLayer);
         this.getActions().addAction(ActionFactory.createRectangularSelectAction(rectangularSelectDecorator, selectLayer, rectangularSelectProvider));
 
-        blockWidgets = new HashMap<InputBlock, BlockWidget>();
-
         boolean b = this.getUndoRedoEnabled();
         this.setUndoRedoEnabled(false);
         this.setNewModel(model);
         this.setUndoRedoEnabled(b);
-    }
-
-    private void selectionUpdated() {
-        getModel().setSelectedNodes(this.getSelectedNodes());
-        addUndo();
+        this.addObjectSceneListener(selectionChangedListener, ObjectSceneEventType.OBJECT_SELECTION_CHANGED, ObjectSceneEventType.OBJECT_HIGHLIGHTING_CHANGED, ObjectSceneEventType.OBJECT_HOVER_CHANGED);
     }
 
     public DiagramViewModel getModel() {
         return model;
     }
 
-    public void setRealZoomFactor(double d) {
-        this.realZoomFactor = d;
-    }
-
-    public double getRealZoomFactor() {
-        if (realZoomFactor == 0.0) {
-            return getZoomFactor();
-        } else {
-            return realZoomFactor;
-        }
-    }
-
     public JScrollPane getScrollPane() {
         return scrollPane;
     }
 
+    @Override
+    public Component getComponent() {
+        return scrollPane;
+    }
+
     public boolean isAllVisible() {
-        return getModel().getHiddenNodes().size() == 0;
+        return getModel().getHiddenNodes().isEmpty();
     }
 
     public Action createGotoAction(final Figure f) {
         final DiagramScene diagramScene = this;
-        Action a = new AbstractAction() {
-
-            public void actionPerformed(ActionEvent e) {
-                diagramScene.gotoFigure(f);
-            }
-        };
-
-        a.setEnabled(true);
-        a.putValue(Action.SMALL_ICON, new ColorIcon(f.getColor()));
         String name = f.getLines()[0];
 
         name += " (";
@@ -469,112 +470,81 @@
         if (f.getCluster() != null) {
             name += "B" + f.getCluster().toString();
         }
-        if (!this.getFigureWidget(f).isVisible()) {
+        final boolean hidden = !this.getWidget(f, FigureWidget.class).isVisible();
+        if (hidden) {
             if (f.getCluster() != null) {
                 name += ", ";
             }
             name += "hidden";
         }
         name += ")";
-        a.putValue(Action.NAME, name);
+        Action a = new AbstractAction(name, new ColorIcon(f.getColor())) {
+
+            @Override
+            public void actionPerformed(ActionEvent e) {
+                diagramScene.gotoFigure(f);
+            }
+        };
+
+        a.setEnabled(true);
         return a;
     }
 
     public void setNewModel(DiagramViewModel model) {
-        if (this.model != null) {
-            this.model.getDiagramChangedEvent().removeListener(this);
-            this.model.getViewPropertiesChangedEvent().removeListener(this);
-        }
+        assert this.model == null : "can set model only once!";
         this.model = model;
+        this.modelCopy = null;
 
-        if (this.model == null) {
-            this.modelCopy = null;
-        } else {
-            this.modelCopy = this.model.copy();
-        }
-
-        model.getDiagramChangedEvent().addListener(this);
-        model.getViewPropertiesChangedEvent().addListener(this);
-
+        model.getDiagramChangedEvent().addListener(fullChange);
+        model.getViewPropertiesChangedEvent().addListener(fullChange);
+        model.getViewChangedEvent().addListener(selectionChange);
+        model.getHiddenNodesChangedEvent().addListener(hiddenNodesChange);
         update();
     }
 
     private void update() {
-
-        /*if (startLabel != null) {
-        // Animate fade-out
-        final LabelWidget labelWidget = this.startLabel;
-        labelWidget.setVisible(true);
-        RequestProcessor.getDefault().post(new Runnable() {
-        public void run() {
-        final int Sleep = 200;
-        final int Progress = 10;
-        for (int i = 0; i < 255 / Progress + 1; i++) {
-        try {
-        SwingUtilities.invokeAndWait(new Runnable() {
-        public void run() {
-        Color c = labelWidget.getForeground();
-        int v = c.getRed();
-        v += Progress;
-        if (v > 255) {
-        v = 255;
-        }
-        labelWidget.setForeground(new Color(v, v, v, 255 - v));
-        labelWidget.getScene().validate();
-        }
-        });
-        } catch (InterruptedException ex) {
-        } catch (InvocationTargetException ex) {
-        }
-        try {
-        Thread.sleep(Sleep);
-        } catch (InterruptedException ex) {
-        }
-        }
-        labelWidget.setVisible(false);
-        DiagramScene.this.scrollChangeListener.unregister(labelWidget);
-        }
-        }, 1000);
-        startLabel = null;
-        }*/
-
-        slotLayer.removeChildren();
         mainLayer.removeChildren();
         blockLayer.removeChildren();
 
-        blockWidgets.clear();
-        figureWidgets = new HashMap<Figure, FigureWidget>();
-        slotWidgets = new HashMap<Slot, SlotWidget>();
-        connectionWidgets = new HashMap<Connection, ConnectionWidget>();
+        rebuilding = true;
 
-        WidgetAction selectAction = new ExtendedSelectAction(selectProvider);
+        Collection<Object> objects = new ArrayList<>(this.getObjects());
+        for (Object o : objects) {
+            this.removeObject(o);
+        }
+
         Diagram d = getModel().getDiagramToView();
 
-        if (getModel().getShowBlocks()) {
+        if (d.getGraph().getBlocks().isEmpty()) {
             Scheduler s = Lookup.getDefault().lookup(Scheduler.class);
-            Collection<InputBlock> newBlocks = new ArrayList<InputBlock>(s.schedule(d.getGraph()));
-            d.schedule(newBlocks);
+            d.getGraph().clearBlocks();
+            s.schedule(d.getGraph());
+            d.getGraph().ensureNodesInBlocks();
+            d.updateBlocks();
         }
 
         for (Figure f : d.getFigures()) {
-            FigureWidget w = new FigureWidget(f, this, mainLayer);
+            FigureWidget w = new FigureWidget(f, hoverAction, selectAction, this, mainLayer);
+            w.getActions().addAction(ActionFactory.createPopupMenuAction(w));
             w.getActions().addAction(selectAction);
             w.getActions().addAction(hoverAction);
-            w.getActions().addAction(ActionFactory.createPopupMenuAction(w));
-            w.getActions().addAction(new DoubleClickAction(w));
             w.setVisible(false);
 
-            figureWidgets.put(f, w);
+            this.addObject(f, w);
 
             for (InputSlot s : f.getInputSlots()) {
-                SlotWidget sw = new InputSlotWidget(s, this, slotLayer, w);
-                slotWidgets.put(s, sw);
+                SlotWidget sw = new InputSlotWidget(s, this, w, w);
+                addObject(s, sw);
+                sw.getActions().addAction(new DoubleClickAction(sw));
+                sw.getActions().addAction(hoverAction);
                 sw.getActions().addAction(selectAction);
             }
 
             for (OutputSlot s : f.getOutputSlots()) {
-                SlotWidget sw = new OutputSlotWidget(s, this, slotLayer, w);
-                slotWidgets.put(s, sw);
+                SlotWidget sw = new OutputSlotWidget(s, this, w, w);
+                addObject(s, sw);
+                sw.getActions().addAction(new DoubleClickAction(sw));
+                sw.getActions().addAction(hoverAction);
                 sw.getActions().addAction(selectAction);
             }
         }
@@ -583,28 +553,30 @@
             for (InputBlock bn : d.getGraph().getBlocks()) {
                 BlockWidget w = new BlockWidget(this, d, bn);
                 w.setVisible(false);
-                blockWidgets.put(bn, w);
+                this.addObject(bn, w);
                 blockLayer.addChild(w);
             }
         }
 
+        rebuilding = false;
         this.smallUpdate(true);
+    }
 
+    public boolean isRebuilding() {
+        return rebuilding;
     }
 
     private void smallUpdate(boolean relayout) {
-
         this.updateHiddenNodes(model.getHiddenNodes(), relayout);
         boolean b = this.getUndoRedoEnabled();
         this.setUndoRedoEnabled(false);
-        this.setSelection(getModel().getSelectedNodes());
         this.setUndoRedoEnabled(b);
         this.validate();
     }
 
     private boolean isVisible(Connection c) {
-        FigureWidget w1 = figureWidgets.get(c.getInputSlot().getFigure());
-        FigureWidget w2 = figureWidgets.get(c.getOutputSlot().getFigure());
+        FigureWidget w1 = getWidget(c.getInputSlot().getFigure());
+        FigureWidget w2 = getWidget(c.getOutputSlot().getFigure());
 
         if (w1.isVisible() && w2.isVisible()) {
             return true;
@@ -614,19 +586,18 @@
     }
 
     private void relayout(Set<Widget> oldVisibleWidgets) {
-
         Diagram diagram = getModel().getDiagramToView();
 
-        HashSet<Figure> figures = new HashSet<Figure>();
+        HashSet<Figure> figures = new HashSet<>();
 
         for (Figure f : diagram.getFigures()) {
-            FigureWidget w = figureWidgets.get(f);
+            FigureWidget w = getWidget(f);
             if (w.isVisible()) {
                 figures.add(f);
             }
         }
 
-        HashSet<Connection> edges = new HashSet<Connection>();
+        HashSet<Connection> edges = new HashSet<>();
 
         for (Connection c : diagram.getConnections()) {
             if (isVisible(c)) {
@@ -635,24 +606,31 @@
         }
 
         if (getModel().getShowBlocks()) {
-            HierarchicalClusterLayoutManager m = new HierarchicalClusterLayoutManager(OldHierarchicalLayoutManager.Combine.SAME_OUTPUTS);
+            HierarchicalClusterLayoutManager m = new HierarchicalClusterLayoutManager(HierarchicalLayoutManager.Combine.SAME_OUTPUTS);
             HierarchicalLayoutManager manager = new HierarchicalLayoutManager(HierarchicalLayoutManager.Combine.SAME_OUTPUTS);
             manager.setMaxLayerLength(9);
             manager.setMinLayerDifference(3);
             m.setManager(manager);
             m.setSubManager(new HierarchicalLayoutManager(HierarchicalLayoutManager.Combine.SAME_OUTPUTS));
             m.doLayout(new LayoutGraph(edges, figures));
-
         } else {
             HierarchicalLayoutManager manager = new HierarchicalLayoutManager(HierarchicalLayoutManager.Combine.SAME_OUTPUTS);
             manager.setMaxLayerLength(10);
             manager.doLayout(new LayoutGraph(edges, figures));
         }
 
+        relayoutWithoutLayout(oldVisibleWidgets);
+    }
+    private Set<Pair<Point, Point>> lineCache = new HashSet<>();
+
+    private void relayoutWithoutLayout(Set<Widget> oldVisibleWidgets) {
+
+        Diagram diagram = getModel().getDiagramToView();
+
         int maxX = -BORDER_SIZE;
         int maxY = -BORDER_SIZE;
         for (Figure f : diagram.getFigures()) {
-            FigureWidget w = figureWidgets.get(f);
+            FigureWidget w = getWidget(f);
             if (w.isVisible()) {
                 Point p = f.getPosition();
                 Dimension d = f.getSize();
@@ -663,8 +641,8 @@
 
         for (Connection c : diagram.getConnections()) {
             List<Point> points = c.getControlPoints();
-            FigureWidget w1 = figureWidgets.get((Figure) c.getTo().getVertex());
-            FigureWidget w2 = figureWidgets.get((Figure) c.getFrom().getVertex());
+            FigureWidget w1 = getWidget((Figure) c.getTo().getVertex());
+            FigureWidget w2 = getWidget((Figure) c.getFrom().getVertex());
             if (w1.isVisible() && w2.isVisible()) {
                 for (Point p : points) {
                     if (p != null) {
@@ -677,7 +655,7 @@
 
         if (getModel().getShowBlocks()) {
             for (Block b : diagram.getBlocks()) {
-                BlockWidget w = blockWidgets.get(b.getInputBlock());
+                BlockWidget w = getWidget(b.getInputBlock());
                 if (w != null && w.isVisible()) {
                     Rectangle r = b.getBounds();
                     maxX = Math.max(maxX, r.x + r.width);
@@ -693,6 +671,8 @@
         int curHeight = maxY + 2 * BORDER_SIZE;
 
         Rectangle bounds = this.getScrollPane().getBounds();
+        bounds.width /= getZoomFactor();
+        bounds.height /= getZoomFactor();
         if (curWidth < bounds.width) {
             offx = (bounds.width - curWidth) / 2;
         }
@@ -708,62 +688,61 @@
         connectionLayer.removeChildren();
         int visibleFigureCount = 0;
         for (Figure f : diagram.getFigures()) {
-            if (figureWidgets.get(f).isVisible()) {
+            if (getWidget(f, FigureWidget.class).isVisible()) {
                 visibleFigureCount++;
             }
         }
 
+
+        Set<Pair<Point, Point>> lastLineCache = lineCache;
+        lineCache = new HashSet<>();
+        for (Figure f : diagram.getFigures()) {
+            for (OutputSlot s : f.getOutputSlots()) {
+                SceneAnimator anim = animator;
+                if (visibleFigureCount > ANIMATION_LIMIT || oldVisibleWidgets == null) {
+                    anim = null;
+                }
+                processOutputSlot(lastLineCache, s, s.getConnections(), 0, null, null, offx2, offy2, anim);
+            }
+        }
+
         for (Figure f : diagram.getFigures()) {
-            for (OutputSlot s : f.getOutputSlots()) {
-                SceneAnimator anim = animator;
-                if (visibleFigureCount > ANIMATION_LIMIT) {
-                    anim = null;
-                }
-                processOutputSlot(s, s.getConnections(), 0, null, null, offx2, offy2, anim);
-            }
-        }
-
-        for (Figure f : diagram.getFigures()) {
-            FigureWidget w = figureWidgets.get(f);
+            FigureWidget w = getWidget(f);
             if (w.isVisible()) {
                 Point p = f.getPosition();
                 Point p2 = new Point(p.x + offx2, p.y + offy2);
-                Rectangle r = new Rectangle(p.x + offx2, p.y + offy2, f.getSize().width, f.getSize().height);
-                if (oldVisibleWidgets.contains(w)) {
-                    if (visibleFigureCount > ANIMATION_LIMIT) {
-                        w.setPreferredLocation(p2);
-                    } else {
-                        animator.animatePreferredLocation(w, p2);
-                    }
+                if ((visibleFigureCount <= ANIMATION_LIMIT && oldVisibleWidgets != null && oldVisibleWidgets.contains(w))) {
+                    animator.animatePreferredLocation(w, p2);
                 } else {
                     w.setPreferredLocation(p2);
+                    animator.animatePreferredLocation(w, p2);
                 }
             }
         }
 
         if (getModel().getShowBlocks()) {
             for (Block b : diagram.getBlocks()) {
-                BlockWidget w = blockWidgets.get(b.getInputBlock());
+                BlockWidget w = getWidget(b.getInputBlock());
                 if (w != null && w.isVisible()) {
                     Point location = new Point(b.getBounds().x + offx2, b.getBounds().y + offy2);
                     Rectangle r = new Rectangle(location.x, location.y, b.getBounds().width, b.getBounds().height);
-                    if (oldVisibleWidgets.contains(w)) {
-                        if (visibleFigureCount > ANIMATION_LIMIT) {
-                            w.setPreferredBounds(r);
-                        } else {
-                            animator.animatePreferredBounds(w, r);
-                        }
+
+                    if ((visibleFigureCount <= ANIMATION_LIMIT && oldVisibleWidgets != null && oldVisibleWidgets.contains(w))) {
+                        animator.animatePreferredBounds(w, r);
                     } else {
                         w.setPreferredBounds(r);
+                        animator.animatePreferredBounds(w, r);
                     }
                 }
             }
         }
+
+        this.validate();
     }
     private final Point specialNullPoint = new Point(Integer.MAX_VALUE, Integer.MAX_VALUE);
 
-    private void processOutputSlot(OutputSlot s, List<Connection> connections, int controlPointIndex, Point lastPoint, LineWidget predecessor, int offx, int offy, SceneAnimator animator) {
-        Map<Point, List<Connection>> pointMap = new HashMap<Point, List<Connection>>();
+    private void processOutputSlot(Set<Pair<Point, Point>> lastLineCache, OutputSlot s, List<Connection> connections, int controlPointIndex, Point lastPoint, LineWidget predecessor, int offx, int offy, SceneAnimator animator) {
+        Map<Point, List<Connection>> pointMap = new HashMap<>(connections.size());
 
         for (Connection c : connections) {
 
@@ -779,16 +758,16 @@
             Point cur = controlPoints.get(controlPointIndex);
             if (cur == null) {
                 cur = specialNullPoint;
-            } else if (controlPointIndex == 0 && !s.getShowName()) {
+            } else if (controlPointIndex == 0 && !s.shouldShowName()) {
                 cur = new Point(cur.x, cur.y - SLOT_OFFSET);
-            } else if (controlPointIndex == controlPoints.size() - 1 && !c.getInputSlot().getShowName()) {
+            } else if (controlPointIndex == controlPoints.size() - 1 && !c.getInputSlot().shouldShowName()) {
                 cur = new Point(cur.x, cur.y + SLOT_OFFSET);
             }
 
             if (pointMap.containsKey(cur)) {
                 pointMap.get(cur).add(c);
             } else {
-                List<Connection> newList = new ArrayList<Connection>(2);
+                List<Connection> newList = new ArrayList<>(2);
                 newList.add(c);
                 pointMap.put(cur, newList);
             }
@@ -814,44 +793,70 @@
 
             LineWidget newPredecessor = predecessor;
             if (p == specialNullPoint) {
-
             } else if (lastPoint == specialNullPoint) {
-
             } else if (lastPoint != null) {
                 Point p1 = new Point(lastPoint.x + offx, lastPoint.y + offy);
                 Point p2 = new Point(p.x + offx, p.y + offy);
-                LineWidget w = new LineWidget(this, s, connectionList, p1, p2, predecessor, animator, isBold, isDashed);
+
+                Pair<Point, Point> curPair = new Pair<>(p1, p2);
+                SceneAnimator curAnimator = animator;
+                if (lastLineCache.contains(curPair)) {
+                    curAnimator = null;
+                }
+                LineWidget w = new LineWidget(this, s, connectionList, p1, p2, predecessor, curAnimator, isBold, isDashed);
+                lineCache.add(curPair);
+
                 newPredecessor = w;
                 connectionLayer.addChild(w);
+                this.addObject(new ConnectionSet(connectionList), w);
                 w.getActions().addAction(hoverAction);
             }
 
-            processOutputSlot(s, connectionList, controlPointIndex + 1, p, newPredecessor, offx, offy, animator);
+            processOutputSlot(lastLineCache, s, connectionList, controlPointIndex + 1, p, newPredecessor, offx, offy, animator);
         }
     }
 
-    private void clearSelection() {
-        if (selectedWidgets.size() == 0) {
-            return;
-        }
-        for (FigureWidget w : selectedWidgets) {
-            assert w.getState().isSelected();
-            w.setState(w.getState().deriveSelected(false));
-            content.remove(w.getNode());
-        }
-        selectedWidgets.clear();
+    @Override
+    public void setInteractionMode(InteractionMode mode) {
+        panAction.setEnabled(mode == InteractionMode.PANNING);
+        // When panAction is not enabled, it does not consume the event
+        // and the selection action handles it instead
     }
 
+    private class ConnectionSet {
+
+        private Set<Connection> connections;
+
+        public ConnectionSet(Collection<Connection> connections) {
+            connections = new HashSet<>(connections);
+        }
+
+        public Set<Connection> getConnectionSet() {
+            return Collections.unmodifiableSet(connections);
+        }
+    }
+
+    @Override
     public Lookup getLookup() {
         return lookup;
     }
 
+    @Override
+    public void initialize() {
+        Figure f = getModel().getDiagramToView().getRootFigure();
+        if (f != null) {
+            setUndoRedoEnabled(false);
+            gotoFigure(f);
+            setUndoRedoEnabled(true);
+        }
+    }
+
     public void gotoFigures(final List<Figure> figures) {
         Rectangle overall = null;
-        showFigures(figures);
+        getModel().showFigures(figures);
         for (Figure f : figures) {
 
-            FigureWidget fw = getFigureWidget(f);
+            FigureWidget fw = getWidget(f);
             if (fw != null) {
                 Rectangle r = fw.getBounds();
                 Point p = fw.getLocation();
@@ -869,6 +874,54 @@
         }
     }
 
+    private Set<Object> idSetToObjectSet(Set<Object> ids) {
+
+        Set<Object> result = new HashSet<>();
+        for (Figure f : getModel().getDiagramToView().getFigures()) {
+            if (DiagramScene.doesIntersect(f.getSource().getSourceNodesAsSet(), ids)) {
+                result.add(f);
+            }
+
+            for (Slot s : f.getSlots()) {
+                if (DiagramScene.doesIntersect(s.getSource().getSourceNodesAsSet(), ids)) {
+                    result.add(s);
+                }
+            }
+        }
+        return result;
+    }
+
+    public void gotoSelection(Set<Object> ids) {
+
+        Rectangle overall = null;
+        Set<Integer> hiddenNodes = new HashSet<>(this.getModel().getHiddenNodes());
+        hiddenNodes.removeAll(ids);
+        this.getModel().showNot(hiddenNodes);
+
+        Set<Object> objects = idSetToObjectSet(ids);
+        for (Object o : objects) {
+
+            Widget w = getWidget(o);
+            if (w != null) {
+                Rectangle r = w.getBounds();
+                Point p = w.convertLocalToScene(new Point(0, 0));
+
+                Rectangle r2 = new Rectangle(p.x, p.y, r.width, r.height);
+
+                if (overall == null) {
+                    overall = r2;
+                } else {
+                    overall = overall.union(r2);
+                }
+            }
+        }
+        if (overall != null) {
+            centerRectangle(overall);
+        }
+
+        setSelectedObjects(objects);
+    }
+
     private Point calcCenter(Rectangle r) {
 
         Point center = new Point((int) r.getCenterX(), (int) r.getCenterY());
@@ -909,63 +962,9 @@
         }
     }
 
-    private void addToSelection(Figure f) {
-        FigureWidget w = getFigureWidget(f);
-        addToSelection(w);
-    }
-
-    private void addToSelection(FigureWidget w) {
-        assert !selectedWidgets.contains(w);
-        selectedWidgets.add(w);
-        content.add(w.getNode());
-        w.setState(w.getState().deriveSelected(true));
-    }
-
-    private void setSelection(Set<Integer> nodes) {
-        clearSelection();
-        for (Figure f : getModel().getDiagramToView().getFigures()) {
-            if (doesIntersect(f.getSource().getSourceNodesAsSet(), nodes)) {
-                addToSelection(f);
-            }
-        }
-        selectionUpdated();
-        this.validate();
-    }
-
+    @Override
     public void setSelection(Collection<Figure> list) {
-        clearSelection();
-        for (Figure f : list) {
-            addToSelection(f);
-        }
-
-        selectionUpdated();
-        this.validate();
-    }
-
-    public Set<Figure> getSelectedFigures() {
-        Set<Figure> result = new HashSet<Figure>();
-        for (Widget w : selectedWidgets) {
-            if (w instanceof FigureWidget) {
-                FigureWidget fw = (FigureWidget) w;
-                if (fw.getState().isSelected()) {
-                    result.add(fw.getFigure());
-                }
-            }
-        }
-        return result;
-    }
-
-    public Set<Integer> getSelectedNodes() {
-        Set<Integer> result = new HashSet<Integer>();
-        for (Widget w : selectedWidgets) {
-            if (w instanceof FigureWidget) {
-                FigureWidget fw = (FigureWidget) w;
-                if (fw.getState().isSelected()) {
-                    result.addAll(fw.getFigure().getSource().getSourceNodesAsSet());
-                }
-            }
-        }
-        return result;
+        super.setSelectedObjects(new HashSet<>(list));
     }
 
     private UndoRedo.Manager getUndoRedoManager() {
@@ -977,6 +976,7 @@
         return undoRedoManager;
     }
 
+    @Override
     public UndoRedo getUndoRedo() {
         return getUndoRedoManager();
     }
@@ -990,9 +990,9 @@
         return true;
     }
 
-    private boolean doesIntersect(Set s1, Set s2) {
+    public static boolean doesIntersect(Set<?> s1, Set<?> s2) {
         if (s1.size() > s2.size()) {
-            Set tmp = s1;
+            Set<?> tmp = s1;
             s1 = s2;
             s2 = tmp;
         }
@@ -1006,35 +1006,36 @@
         return false;
     }
 
-    public void showNot(final Set<Integer> nodes) {
-        updateHiddenNodes(nodes, true);
+    @Override
+    public void componentHidden() {
+        SelectionCoordinator.getInstance().getHighlightedChangedEvent().removeListener(highlightedCoordinatorListener);
+        SelectionCoordinator.getInstance().getSelectedChangedEvent().removeListener(selectedCoordinatorListener);
     }
 
-    public void showOnly(final Set<Integer> nodes) {
-        HashSet<Integer> allNodes = new HashSet<Integer>(getModel().getGraphToView().getGroup().getAllNodes());
-        allNodes.removeAll(nodes);
-        updateHiddenNodes(allNodes, true);
+    @Override
+    public void componentShowing() {
+        SelectionCoordinator.getInstance().getHighlightedChangedEvent().addListener(highlightedCoordinatorListener);
+        SelectionCoordinator.getInstance().getSelectedChangedEvent().addListener(selectedCoordinatorListener);
     }
 
     private void updateHiddenNodes(Set<Integer> newHiddenNodes, boolean doRelayout) {
 
-        Set<InputBlock> visibleBlocks = new HashSet<InputBlock>();
-
         Diagram diagram = getModel().getDiagramToView();
         assert diagram != null;
 
-        Set<Widget> oldVisibleWidgets = new HashSet<Widget>();
+        Set<InputBlock> visibleBlocks = new HashSet<InputBlock>();
+        Set<Widget> oldVisibleWidgets = new HashSet<>();
 
         for (Figure f : diagram.getFigures()) {
-            FigureWidget w = figureWidgets.get(f);
-            if (w.isVisible()) {
+            FigureWidget w = getWidget(f);
+            if (w != null && w.isVisible()) {
                 oldVisibleWidgets.add(w);
             }
         }
 
         if (getModel().getShowBlocks()) {
             for (InputBlock b : diagram.getGraph().getBlocks()) {
-                BlockWidget w = blockWidgets.get(b);
+                BlockWidget w = getWidget(b);
                 if (w.isVisible()) {
                     oldVisibleWidgets.add(w);
                 }
@@ -1044,7 +1045,7 @@
         for (Figure f : diagram.getFigures()) {
             boolean hiddenAfter = doesIntersect(f.getSource().getSourceNodesAsSet(), newHiddenNodes);
 
-            FigureWidget w = this.figureWidgets.get(f);
+            FigureWidget w = getWidget(f);
             w.setBoundary(false);
             if (!hiddenAfter) {
                 // Figure is shown
@@ -1059,16 +1060,16 @@
         }
 
         if (getModel().getShowNodeHull()) {
-            List<FigureWidget> boundaries = new ArrayList<FigureWidget>();
+            List<FigureWidget> boundaries = new ArrayList<>();
             for (Figure f : diagram.getFigures()) {
-                FigureWidget w = this.figureWidgets.get(f);
+                FigureWidget w = getWidget(f);
                 if (!w.isVisible()) {
-                    Set<Figure> set = new HashSet<Figure>(f.getPredecessorSet());
+                    Set<Figure> set = new HashSet<>(f.getPredecessorSet());
                     set.addAll(f.getSuccessorSet());
 
                     boolean b = false;
                     for (Figure neighbor : set) {
-                        FigureWidget neighborWidget = figureWidgets.get(neighbor);
+                        FigureWidget neighborWidget = getWidget(neighbor);
                         if (neighborWidget.isVisible()) {
                             b = true;
                             break;
@@ -1097,7 +1098,7 @@
 
                 boolean visibleAfter = visibleBlocks.contains(b);
 
-                BlockWidget w = blockWidgets.get(b);
+                BlockWidget w = getWidget(b);
                 if (visibleAfter) {
                     // Block must be shown
                     w.setVisible(true);
@@ -1108,7 +1109,6 @@
             }
         }
 
-        getModel().setHiddenNodes(newHiddenNodes);
         if (doRelayout) {
             relayout(oldVisibleWidgets);
         }
@@ -1116,51 +1116,50 @@
         addUndo();
     }
 
-    private void showFigures(Collection<Figure> f) {
-        HashSet<Integer> newHiddenNodes = new HashSet<Integer>(getModel().getHiddenNodes());
-        for (Figure fig : f) {
-            newHiddenNodes.removeAll(fig.getSource().getSourceNodesAsSet());
-        }
-        updateHiddenNodes(newHiddenNodes, true);
-    }
-
     private void showFigure(Figure f) {
-        HashSet<Integer> newHiddenNodes = new HashSet<Integer>(getModel().getHiddenNodes());
+        HashSet<Integer> newHiddenNodes = new HashSet<>(getModel().getHiddenNodes());
         newHiddenNodes.removeAll(f.getSource().getSourceNodesAsSet());
-        updateHiddenNodes(newHiddenNodes, true);
-    }
-
-    public void showAll(final Collection<Figure> f) {
-        showFigures(f);
-
+        this.model.setHiddenNodes(newHiddenNodes);
     }
 
     public void show(final Figure f) {
         showFigure(f);
     }
 
+    public void setSelectedObjects(Object... args) {
+        Set<Object> set = new HashSet<>();
+        for (Object o : args) {
+            set.add(o);
+        }
+        super.setSelectedObjects(set);
+    }
+
+    private void centerWidget(Widget w) {
+        Rectangle r = w.getBounds();
+        Point p = w.getLocation();
+        centerRectangle(new Rectangle(p.x, p.y, r.width, r.height));
+    }
+
     public void gotoFigure(final Figure f) {
-
         if (!isVisible(f)) {
             showFigure(f);
         }
 
-        FigureWidget fw = getFigureWidget(f);
+        FigureWidget fw = getWidget(f);
         if (fw != null) {
-            Rectangle r = fw.getBounds();
-            Point p = fw.getLocation();
-            centerRectangle(new Rectangle(p.x, p.y, r.width, r.height));
-
-            // Select figure
-            clearSelection();
-            addToSelection(fw);
-            selectionUpdated();
+            centerWidget(fw);
+            setSelection(Arrays.asList(f));
         }
     }
 
     public JPopupMenu createPopupMenu() {
         JPopupMenu menu = new JPopupMenu();
-        for (Action a : actions) {
+
+        Action[] currentActions = actionsWithSelection;
+        if (this.getSelectedObjects().isEmpty()) {
+            currentActions = actions;
+        }
+        for (Action a : currentActions) {
             if (a == null) {
                 menu.addSeparator();
             } else {
@@ -1208,6 +1207,7 @@
 
             SwingUtilities.invokeLater(new Runnable() {
 
+                @Override
                 public void run() {
                     scene.setScrollPosition(oldScrollPosition);
                 }
@@ -1216,9 +1216,10 @@
             scene.setUndoRedoEnabled(b);
         }
 
+        @Override
         public void changed(DiagramViewModel source) {
             scene.getModel().getViewChangedEvent().removeListener(this);
-            if (oldModel.getSelectedNodes().equals(newModel.getHiddenNodes())) {
+            if (oldModel.getHiddenNodes().equals(newModel.getHiddenNodes())) {
                 scene.smallUpdate(false);
             } else {
                 scene.smallUpdate(true);
@@ -1235,11 +1236,33 @@
         return undoRedoEnabled;
     }
 
-    public void changed(DiagramViewModel source) {
-        assert source == model : "Receive only changed event from current model!";
-        assert source != null;
-        update();
-    }
+    private final ChangedListener<DiagramViewModel> fullChange = new ChangedListener<DiagramViewModel>() {
+        @Override
+        public void changed(DiagramViewModel source) {
+            assert source == model : "Receive only changed event from current model!";
+            assert source != null;
+            update();
+        }
+    };
+
+    private final ChangedListener<DiagramViewModel> hiddenNodesChange = new ChangedListener<DiagramViewModel>() {
+        @Override
+        public void changed(DiagramViewModel source) {
+            assert source == model : "Receive only changed event from current model!";
+            assert source != null;
+            smallUpdate(true);
+        }
+    };
+
+    private final ChangedListener<DiagramViewModel> selectionChange = new ChangedListener<DiagramViewModel>() {
+        @Override
+        public void changed(DiagramViewModel source) {
+            assert source == model : "Receive only changed event from current model!";
+            assert source != null;
+            smallUpdate(false);
+        }
+    };
+
 
     private void addUndo() {
 
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/DiagramViewModel.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/DiagramViewModel.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2008, 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
@@ -24,22 +24,16 @@
  */
 package com.sun.hotspot.igv.view;
 
-import com.sun.hotspot.igv.data.Group;
-import com.sun.hotspot.igv.data.InputGraph;
-import com.sun.hotspot.igv.data.InputNode;
+import com.sun.hotspot.igv.data.*;
 import com.sun.hotspot.igv.difference.Difference;
+import com.sun.hotspot.igv.filter.CustomFilter;
 import com.sun.hotspot.igv.filter.FilterChain;
 import com.sun.hotspot.igv.graph.Diagram;
-import com.sun.hotspot.igv.data.ChangedEvent;
+import com.sun.hotspot.igv.graph.Figure;
+import com.sun.hotspot.igv.settings.Settings;
 import com.sun.hotspot.igv.util.RangeSliderModel;
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Set;
-import com.sun.hotspot.igv.data.ChangedListener;
-import com.sun.hotspot.igv.settings.Settings;
 import java.awt.Color;
+import java.util.*;
 
 /**
  *
@@ -49,20 +43,25 @@
 
     // Warning: Update setData method if fields are added
     private Group group;
+    private ArrayList<InputGraph> graphs;
     private Set<Integer> hiddenNodes;
     private Set<Integer> onScreenNodes;
     private Set<Integer> selectedNodes;
     private FilterChain filterChain;
     private FilterChain sequenceFilterChain;
     private Diagram diagram;
+    private InputGraph inputGraph;
     private ChangedEvent<DiagramViewModel> groupChangedEvent;
     private ChangedEvent<DiagramViewModel> diagramChangedEvent;
     private ChangedEvent<DiagramViewModel> viewChangedEvent;
+    private ChangedEvent<DiagramViewModel> hiddenNodesChangedEvent;
     private ChangedEvent<DiagramViewModel> viewPropertiesChangedEvent;
     private boolean showBlocks;
     private boolean showNodeHull;
+    private boolean hideDuplicates;
     private ChangedListener<FilterChain> filterChainChangedListener = new ChangedListener<FilterChain>() {
 
+        @Override
         public void changed(FilterChain source) {
             diagramChanged();
         }
@@ -75,6 +74,10 @@
         return result;
     }
 
+    public Group getGroup() {
+        return group;
+    }
+
     public void setData(DiagramViewModel newModel) {
         super.setData(newModel);
         boolean diagramChanged = false;
@@ -83,6 +86,10 @@
 
         boolean groupChanged = (group == newModel.group);
         this.group = newModel.group;
+        if (groupChanged) {
+            filterGraphs();
+        }
+
         diagramChanged |= (filterChain != newModel.filterChain);
         this.filterChain = newModel.filterChain;
         diagramChanged |= (sequenceFilterChain != newModel.sequenceFilterChain);
@@ -100,7 +107,7 @@
         viewPropertiesChanged |= (showNodeHull != newModel.showNodeHull);
         this.showNodeHull = newModel.showNodeHull;
 
-        if(groupChanged) {
+        if (groupChanged) {
             groupChangedEvent.fire();
         }
 
@@ -133,53 +140,75 @@
         viewPropertiesChangedEvent.fire();
     }
 
-    public DiagramViewModel(Group g, FilterChain filterChain, FilterChain sequenceFilterChain) {
-        super(calculateStringList(g));
+    public boolean getHideDuplicates() {
+        return hideDuplicates;
+    }
 
+    public void setHideDuplicates(boolean b) {
+        System.err.println("setHideDuplicates: " + b);
+        hideDuplicates = b;
+        InputGraph currentGraph = getFirstGraph();
+        if (hideDuplicates) {
+            // Back up to the unhidden equivalent graph
+            int index = graphs.indexOf(currentGraph);
+            while (graphs.get(index).getProperties().get("_isDuplicate") != null) {
+                index--;
+            }
+            currentGraph = graphs.get(index);
+        }
+        filterGraphs();
+        selectGraph(currentGraph);
+        viewPropertiesChangedEvent.fire();
+    }
+
+    public DiagramViewModel(Group g, FilterChain filterChain, FilterChain sequenceFilterChain) {
+        super(Arrays.asList("default"));
+
+        this.showBlocks = false;
         this.showNodeHull = true;
-        this.showBlocks = true;
         this.group = g;
+        filterGraphs();
         assert filterChain != null;
         this.filterChain = filterChain;
         assert sequenceFilterChain != null;
         this.sequenceFilterChain = sequenceFilterChain;
-        hiddenNodes = new HashSet<Integer>();
-        onScreenNodes = new HashSet<Integer>();
-        selectedNodes = new HashSet<Integer>();
+        hiddenNodes = new HashSet<>();
+        onScreenNodes = new HashSet<>();
+        selectedNodes = new HashSet<>();
         super.getChangedEvent().addListener(this);
-        diagramChangedEvent = new ChangedEvent<DiagramViewModel>(this);
-        viewChangedEvent = new ChangedEvent<DiagramViewModel>(this);
-        viewPropertiesChangedEvent = new ChangedEvent<DiagramViewModel>(this);
-        groupChangedEvent = new ChangedEvent<DiagramViewModel>(this);
+        diagramChangedEvent = new ChangedEvent<>(this);
+        viewChangedEvent = new ChangedEvent<>(this);
+        hiddenNodesChangedEvent = new ChangedEvent<>(this);
+        viewPropertiesChangedEvent = new ChangedEvent<>(this);
+
+        groupChangedEvent = new ChangedEvent<>(this);
         groupChangedEvent.addListener(groupChangedListener);
         groupChangedEvent.fire();
 
         filterChain.getChangedEvent().addListener(filterChainChangedListener);
         sequenceFilterChain.getChangedEvent().addListener(filterChainChangedListener);
     }
-
     private final ChangedListener<DiagramViewModel> groupChangedListener = new ChangedListener<DiagramViewModel>() {
 
         private Group oldGroup;
 
+        @Override
         public void changed(DiagramViewModel source) {
-            if(oldGroup != null) {
+            if (oldGroup != null) {
                 oldGroup.getChangedEvent().removeListener(groupContentChangedListener);
             }
             group.getChangedEvent().addListener(groupContentChangedListener);
             oldGroup = group;
         }
     };
-
-
     private final ChangedListener<Group> groupContentChangedListener = new ChangedListener<Group>() {
 
+        @Override
         public void changed(Group source) {
             assert source == group;
-            setPositions(calculateStringList(source));
+            filterGraphs();
             setSelectedNodes(selectedNodes);
         }
-
     };
 
     public ChangedEvent<DiagramViewModel> getDiagramChangedEvent() {
@@ -190,25 +219,29 @@
         return viewChangedEvent;
     }
 
+    public ChangedEvent<DiagramViewModel> getHiddenNodesChangedEvent() {
+        return hiddenNodesChangedEvent;
+    }
+
     public ChangedEvent<DiagramViewModel> getViewPropertiesChangedEvent() {
         return viewPropertiesChangedEvent;
     }
 
     public Set<Integer> getSelectedNodes() {
-        return Collections.unmodifiableSet(selectedNodes);
+        return selectedNodes;
     }
 
     public Set<Integer> getHiddenNodes() {
-        return Collections.unmodifiableSet(hiddenNodes);
+        return hiddenNodes;
     }
 
     public Set<Integer> getOnScreenNodes() {
-        return Collections.unmodifiableSet(onScreenNodes);
+        return onScreenNodes;
     }
 
     public void setSelectedNodes(Set<Integer> nodes) {
         this.selectedNodes = nodes;
-        List<Color> colors = new ArrayList<Color>();
+        List<Color> colors = new ArrayList<>();
         for (String s : getPositions()) {
             colors.add(Color.black);
         }
@@ -219,14 +252,14 @@
                 }
                 InputNode last = null;
                 int index = 0;
-                for (InputGraph g : group.getGraphs()) {
+                for (InputGraph g : graphs) {
                     Color curColor = colors.get(index);
                     InputNode cur = g.getNode(id);
                     if (cur != null) {
                         if (last == null) {
                             curColor = Color.green;
                         } else {
-                            if (last.equals(cur)) {
+                            if (last.equals(cur) && last.getProperties().equals(cur.getProperties())) {
                                 if (curColor == Color.black) {
                                     curColor = Color.white;
                                 }
@@ -242,15 +275,49 @@
                     index++;
                 }
             }
-            this.setColors(colors);
         }
         setColors(colors);
         viewChangedEvent.fire();
     }
 
+    public void showNot(final Set<Integer> nodes) {
+        setHiddenNodes(nodes);
+    }
+
+    public void showFigures(Collection<Figure> f) {
+        HashSet<Integer> newHiddenNodes = new HashSet<>(getHiddenNodes());
+        for (Figure fig : f) {
+            newHiddenNodes.removeAll(fig.getSource().getSourceNodesAsSet());
+        }
+        setHiddenNodes(newHiddenNodes);
+    }
+
+
+    public Set<Figure> getSelectedFigures() {
+        Set<Figure> result = new HashSet<>();
+        for (Figure f : diagram.getFigures()) {
+            for (InputNode node : f.getSource().getSourceNodes()) {
+                if (getSelectedNodes().contains(node.getId())) {
+                    result.add(f);
+                }
+            }
+        }
+        return result;
+    }
+
+    public void showAll(final Collection<Figure> f) {
+        showFigures(f);
+    }
+
+    public void showOnly(final Set<Integer> nodes) {
+        final HashSet<Integer> allNodes = new HashSet<>(getGraphToView().getGroup().getAllNodes());
+        allNodes.removeAll(nodes);
+        setHiddenNodes(allNodes);
+    }
+
     public void setHiddenNodes(Set<Integer> nodes) {
         this.hiddenNodes = nodes;
-        viewChangedEvent.fire();
+        hiddenNodesChangedEvent.fire();
     }
 
     public void setOnScreenNodes(Set<Integer> onScreenNodes) {
@@ -289,27 +356,44 @@
         diagramChanged();
     }
 
-    private static List<String> calculateStringList(Group g) {
-        List<String> result = new ArrayList<String>();
-        for (InputGraph graph : g.getGraphs()) {
-            result.add(graph.getName());
+    /*
+     * Select the set of graphs to be presented.
+     */
+    private void filterGraphs() {
+        ArrayList<InputGraph> result = new ArrayList<>();
+        List<String> positions = new ArrayList<>();
+        for (InputGraph graph : group.getGraphs()) {
+            String duplicate = graph.getProperties().get("_isDuplicate");
+            if (duplicate == null || !hideDuplicates) {
+                result.add(graph);
+                positions.add(graph.getName());
+            }
         }
-        return result;
+        this.graphs = result;
+        setPositions(positions);
     }
 
     public InputGraph getFirstGraph() {
-        return group.getGraphs().get(getFirstPosition());
+        if (getFirstPosition() < graphs.size()) {
+            return graphs.get(getFirstPosition());
+        }
+        return graphs.get(graphs.size() - 1);
     }
 
     public InputGraph getSecondGraph() {
-        List<InputGraph> graphs = group.getGraphs();
-        if (graphs.size() >= getSecondPosition())
-            return group.getGraphs().get(getSecondPosition());
+        if (getSecondPosition() < graphs.size()) {
+            return graphs.get(getSecondPosition());
+        }
         return getFirstGraph();
     }
 
     public void selectGraph(InputGraph g) {
-        int index = group.getGraphs().indexOf(g);
+        int index = graphs.indexOf(g);
+        if (index == -1 && hideDuplicates) {
+            // A graph was selected that's currently hidden, so unhide and select it.
+            setHideDuplicates(false);
+            index = graphs.indexOf(g);
+        }
         assert index != -1;
         setPositions(index, index);
     }
@@ -319,22 +403,47 @@
         if (diagram == null) {
             diagram = Diagram.createDiagram(getGraphToView(), Settings.get().get(Settings.NODE_TEXT, Settings.NODE_TEXT_DEFAULT));
             getFilterChain().apply(diagram, getSequenceFilterChain());
+            if (getFirstPosition() != getSecondPosition()) {
+                CustomFilter f = new CustomFilter(
+                        "difference", "colorize('state', 'same', white);"
+                        + "colorize('state', 'changed', orange);"
+                        + "colorize('state', 'new', green);"
+                        + "colorize('state', 'deleted', red);");
+                f.apply(diagram);
+           }
         }
 
         return diagram;
     }
 
     public InputGraph getGraphToView() {
-        if (getFirstGraph() != getSecondGraph()) {
-            InputGraph inputGraph = Difference.createDiffGraph(getSecondGraph(), getFirstGraph());
-            return inputGraph;
-        } else {
-            InputGraph inputGraph = getFirstGraph();
-            return inputGraph;
+        if (inputGraph == null) {
+            if (getFirstGraph() != getSecondGraph()) {
+                inputGraph = Difference.createDiffGraph(getFirstGraph(), getSecondGraph());
+            } else {
+                inputGraph = getFirstGraph();
+            }
         }
+
+        return inputGraph;
     }
 
+    @Override
     public void changed(RangeSliderModel source) {
+        inputGraph = null;
         diagramChanged();
     }
+
+    void setSelectedFigures(List<Figure> list) {
+        Set<Integer> newSelectedNodes = new HashSet<>();
+        for (Figure f : list) {
+            newSelectedNodes.addAll(f.getSource().getSourceNodesAsSet());
+        }
+        this.setSelectedNodes(newSelectedNodes);
+    }
+
+    void close() {
+        filterChain.getChangedEvent().removeListener(filterChainChangedListener);
+        sequenceFilterChain.getChangedEvent().removeListener(filterChainChangedListener);
 }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/DiagramViewer.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,73 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+
+package com.sun.hotspot.igv.view;
+
+import com.sun.hotspot.igv.graph.Figure;
+import java.awt.Component;
+import java.awt.Graphics2D;
+import java.util.Collection;
+import java.util.List;
+import javax.swing.JComponent;
+import org.openide.awt.UndoRedo;
+import org.openide.util.Lookup;
+
+/**
+ *
+ * @author Thomas Wuerthinger
+ */
+interface DiagramViewer {
+
+    enum InteractionMode {
+        SELECTION,
+        PANNING,
+    }
+
+    public void paint(Graphics2D svgGenerator);
+
+    public Lookup getLookup();
+
+    public JComponent createSatelliteView();
+
+    public Component getComponent();
+
+    public void zoomOut();
+
+    public void zoomIn();
+
+    public UndoRedo getUndoRedo();
+
+    public void componentHidden();
+
+    public void componentShowing();
+
+    public void initialize();
+
+    public void setSelection(Collection<Figure> list);
+
+    public void centerFigures(List<Figure> list);
+
+    public void setInteractionMode(InteractionMode mode);
+
+}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/EditorInputGraphProvider.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/EditorInputGraphProvider.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2007, 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,8 +25,8 @@
 package com.sun.hotspot.igv.view;
 
 import com.sun.hotspot.igv.data.InputGraph;
+import com.sun.hotspot.igv.data.InputNode;
 import com.sun.hotspot.igv.data.services.InputGraphProvider;
-import com.sun.hotspot.igv.data.InputNode;
 import java.util.Set;
 
 /**
@@ -35,18 +35,19 @@
  */
 public class EditorInputGraphProvider implements InputGraphProvider {
 
-    public InputGraph getGraph() {
-        EditorTopComponent e = EditorTopComponent.getActive();
-        if (e == null) {
-            return null;
-        }
-        return e.getDiagramModel().getGraphToView();
+    private EditorTopComponent editor;
+
+    public EditorInputGraphProvider(EditorTopComponent editor) {
+        this.editor = editor;
     }
 
+    @Override
+    public InputGraph getGraph() {
+        return editor.getDiagramModel().getGraphToView();
+    }
+
+    @Override
     public void setSelectedNodes(Set<InputNode> nodes) {
-        EditorTopComponent e = EditorTopComponent.getActive();
-        if (e != null) {
-            e.setSelectedNodes(nodes);
-        }
+        editor.setSelectedNodes(nodes);
     }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/EditorTopComponent.form	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/EditorTopComponent.form	Wed Jul 05 20:35:10 2017 +0200
@@ -18,6 +18,8 @@
   </NonVisualComponents>
   <AuxValues>
     <AuxValue name="FormSettings_autoResourcing" type="java.lang.Integer" value="0"/>
+    <AuxValue name="FormSettings_autoSetComponentName" type="java.lang.Boolean" value="false"/>
+    <AuxValue name="FormSettings_generateFQN" type="java.lang.Boolean" value="true"/>
     <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="true"/>
     <AuxValue name="FormSettings_i18nAutoMode" type="java.lang.Boolean" value="false"/>
     <AuxValue name="FormSettings_layoutCodeTarget" type="java.lang.Integer" value="2"/>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/EditorTopComponent.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/EditorTopComponent.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,62 +23,35 @@
  */
 package com.sun.hotspot.igv.view;
 
+import com.sun.hotspot.igv.data.ChangedEvent;
+import com.sun.hotspot.igv.data.ChangedListener;
 import com.sun.hotspot.igv.data.InputNode;
+import com.sun.hotspot.igv.data.Properties;
+import com.sun.hotspot.igv.data.Properties.PropertyMatcher;
+import com.sun.hotspot.igv.data.services.InputGraphProvider;
 import com.sun.hotspot.igv.filter.FilterChain;
+import com.sun.hotspot.igv.filter.FilterChainProvider;
 import com.sun.hotspot.igv.graph.Diagram;
 import com.sun.hotspot.igv.graph.Figure;
-import com.sun.hotspot.igv.view.actions.EnableBlockLayoutAction;
-import com.sun.hotspot.igv.view.actions.ExpandPredecessorsAction;
-import com.sun.hotspot.igv.view.actions.ExpandSuccessorsAction;
-import com.sun.hotspot.igv.view.actions.ExtractAction;
-import com.sun.hotspot.igv.view.actions.HideAction;
-import com.sun.hotspot.igv.view.actions.NextDiagramAction;
-import com.sun.hotspot.igv.view.actions.NodeFindAction;
-import com.sun.hotspot.igv.view.actions.OverviewAction;
-import com.sun.hotspot.igv.view.actions.PredSuccAction;
-import com.sun.hotspot.igv.view.actions.PrevDiagramAction;
-import com.sun.hotspot.igv.view.actions.ShowAllAction;
-import com.sun.hotspot.igv.view.actions.ZoomInAction;
-import com.sun.hotspot.igv.view.actions.ZoomOutAction;
-import com.sun.hotspot.igv.data.ChangedListener;
-import com.sun.hotspot.igv.data.Properties;
-import com.sun.hotspot.igv.data.Properties.PropertyMatcher;
-import com.sun.hotspot.igv.filter.FilterChainProvider;
+import com.sun.hotspot.igv.graph.services.DiagramProvider;
+import com.sun.hotspot.igv.svg.BatikSVG;
+import com.sun.hotspot.igv.util.LookupHistory;
 import com.sun.hotspot.igv.util.RangeSlider;
-import com.sun.hotspot.igv.util.RangeSliderModel;
-import com.sun.hotspot.igv.svg.BatikSVG;
-import java.awt.BorderLayout;
-import java.awt.CardLayout;
-import java.awt.Color;
-import java.awt.Dimension;
-import java.awt.Graphics2D;
-import java.awt.Point;
+import com.sun.hotspot.igv.view.actions.*;
+import java.awt.*;
 import java.awt.event.HierarchyBoundsListener;
 import java.awt.event.HierarchyEvent;
 import java.awt.event.KeyEvent;
 import java.awt.event.KeyListener;
 import java.beans.PropertyChangeEvent;
 import java.beans.PropertyChangeListener;
-import java.io.File;
-import java.io.FileNotFoundException;
-import java.io.FileOutputStream;
-import java.io.IOException;
-import java.io.OutputStreamWriter;
-import java.io.UnsupportedEncodingException;
-import java.io.Writer;
-import java.util.ArrayList;
-import java.util.HashSet;
+import java.io.*;
 import java.util.List;
-import java.util.Set;
-import javax.swing.Action;
-import javax.swing.ActionMap;
-import javax.swing.JPanel;
-import javax.swing.JToggleButton;
-import javax.swing.SwingUtilities;
-import javax.swing.UIManager;
+import java.util.*;
+import javax.swing.*;
 import javax.swing.border.Border;
 import org.openide.DialogDisplayer;
-import org.openide.actions.FindAction;
+import org.openide.NotifyDescriptor;
 import org.openide.actions.RedoAction;
 import org.openide.actions.UndoAction;
 import org.openide.awt.Toolbar;
@@ -86,40 +59,44 @@
 import org.openide.awt.UndoRedo;
 import org.openide.util.Lookup;
 import org.openide.util.NbBundle;
-import org.openide.util.actions.CallbackSystemAction;
-import org.openide.util.actions.SystemAction;
+import org.openide.util.Utilities;
+import org.openide.util.actions.Presenter;
 import org.openide.util.lookup.AbstractLookup;
 import org.openide.util.lookup.InstanceContent;
 import org.openide.util.lookup.ProxyLookup;
 import org.openide.windows.Mode;
 import org.openide.windows.TopComponent;
 import org.openide.windows.WindowManager;
-import org.openide.NotifyDescriptor;
 
 /**
  *
  * @author Thomas Wuerthinger
  */
-public final class EditorTopComponent extends TopComponent implements ChangedListener<RangeSliderModel>, PropertyChangeListener {
+public final class EditorTopComponent extends TopComponent implements PropertyChangeListener {
 
-    private DiagramScene scene;
+    private DiagramViewer scene;
     private InstanceContent content;
-    private FindPanel findPanel;
+    private InstanceContent graphContent;
     private EnableBlockLayoutAction blockLayoutAction;
     private OverviewAction overviewAction;
+    private HideDuplicatesAction hideDuplicatesAction;
     private PredSuccAction predSuccAction;
+    private SelectionModeAction selectionModeAction;
+    private PanModeAction panModeAction;
     private boolean notFirstTime;
-    private ExtendedSatelliteComponent satelliteComponent;
+    private JComponent satelliteComponent;
     private JPanel centerPanel;
     private CardLayout cardLayout;
     private RangeSlider rangeSlider;
     private JToggleButton overviewButton;
+    private JToggleButton hideDuplicatesButton;
     private static final String PREFERRED_ID = "EditorTopComponent";
     private static final String SATELLITE_STRING = "satellite";
     private static final String SCENE_STRING = "scene";
     private DiagramViewModel rangeSliderModel;
     private ExportCookie exportCookie = new ExportCookie() {
 
+        @Override
         public void export(File f) {
 
             Graphics2D svgGenerator = BatikSVG.createGraphicsObject();
@@ -152,12 +129,32 @@
         }
     };
 
+    private DiagramProvider diagramProvider = new DiagramProvider() {
+
+        @Override
+        public Diagram getDiagram() {
+            return getModel().getDiagramToView();
+        }
+
+        @Override
+        public ChangedEvent<DiagramProvider> getChangedEvent() {
+            return diagramChangedEvent;
+        }
+    };
+
+    private ChangedEvent<DiagramProvider> diagramChangedEvent = new ChangedEvent<>(diagramProvider);
+
+
     private void updateDisplayName() {
         setDisplayName(getDiagram().getName());
+        setToolTipText(getDiagram().getGraph().getGroup().getName());
     }
 
     public EditorTopComponent(Diagram diagram) {
 
+        LookupHistory.init(InputGraphProvider.class);
+        LookupHistory.init(DiagramProvider.class);
+        this.setFocusable(true);
         FilterChain filterChain = null;
         FilterChain sequence = null;
         FilterChainProvider provider = Lookup.getDefault().lookup(FilterChainProvider.class);
@@ -182,16 +179,19 @@
             null,
             ZoomInAction.get(ZoomInAction.class),
             ZoomOutAction.get(ZoomOutAction.class),
+        };
+
+
+        Action[] actionsWithSelection = new Action[]{
+            ExtractAction.get(ExtractAction.class),
+            ShowAllAction.get(HideAction.class),
             null,
             ExpandPredecessorsAction.get(ExpandPredecessorsAction.class),
             ExpandSuccessorsAction.get(ExpandSuccessorsAction.class)
         };
 
-
         initComponents();
 
-        ActionMap actionMap = getActionMap();
-
         ToolbarPool.getDefault().setPreferredIconSize(16);
         Toolbar toolBar = new Toolbar();
         Border b = (Border) UIManager.get("Nb.Editor.Toolbar.border"); //NOI18N
@@ -202,24 +202,30 @@
         container.add(BorderLayout.NORTH, toolBar);
 
         rangeSliderModel = new DiagramViewModel(diagram.getGraph().getGroup(), filterChain, sequence);
-        rangeSliderModel.selectGraph(diagram.getGraph());
         rangeSlider = new RangeSlider();
         rangeSlider.setModel(rangeSliderModel);
-        rangeSliderModel.getChangedEvent().addListener(this);
-        container.add(BorderLayout.CENTER, rangeSlider);
+        JScrollPane pane = new JScrollPane(rangeSlider, ScrollPaneConstants.VERTICAL_SCROLLBAR_NEVER, ScrollPaneConstants.HORIZONTAL_SCROLLBAR_AS_NEEDED);
+        container.add(BorderLayout.CENTER, pane);
 
-        scene = new DiagramScene(actions, rangeSliderModel);
+        scene = new DiagramScene(actions, actionsWithSelection, rangeSliderModel);
         content = new InstanceContent();
-        this.associateLookup(new ProxyLookup(new Lookup[]{scene.getLookup(), new AbstractLookup(content)}));
+        graphContent = new InstanceContent();
+        this.associateLookup(new ProxyLookup(new Lookup[]{scene.getLookup(), new AbstractLookup(graphContent), new AbstractLookup(content)}));
         content.add(exportCookie);
         content.add(rangeSliderModel);
+        content.add(diagramProvider);
+
+        rangeSliderModel.getDiagramChangedEvent().addListener(diagramChangedListener);
+        rangeSliderModel.selectGraph(diagram.getGraph());
+        rangeSliderModel.getViewPropertiesChangedEvent().addListener(new ChangedListener<DiagramViewModel>() {
+                @Override
+                public void changed(DiagramViewModel source) {
+                    hideDuplicatesButton.setSelected(getModel().getHideDuplicates());
+                    hideDuplicatesAction.setState(getModel().getHideDuplicates());
+                }
+            });
 
 
-        findPanel = new FindPanel(diagram.getFigures());
-        findPanel.setMaximumSize(new Dimension(200, 50));
-        toolBar.add(findPanel);
-        toolBar.add(NodeFindAction.get(NodeFindAction.class));
-        toolBar.addSeparator();
         toolBar.add(NextDiagramAction.get(NextDiagramAction.class));
         toolBar.add(PrevDiagramAction.get(PrevDiagramAction.class));
         toolBar.addSeparator();
@@ -232,7 +238,7 @@
 
         blockLayoutAction = new EnableBlockLayoutAction();
         JToggleButton button = new JToggleButton(blockLayoutAction);
-        button.setSelected(true);
+        button.setSelected(false);
         toolBar.add(button);
         blockLayoutAction.addPropertyChangeListener(this);
 
@@ -248,59 +254,91 @@
         toolBar.add(button);
         predSuccAction.addPropertyChangeListener(this);
 
+        hideDuplicatesAction = new HideDuplicatesAction();
+        hideDuplicatesButton = new JToggleButton(hideDuplicatesAction);
+        hideDuplicatesButton.setSelected(false);
+        toolBar.add(hideDuplicatesButton);
+        hideDuplicatesAction.addPropertyChangeListener(this);
+
         toolBar.addSeparator();
         toolBar.add(UndoAction.get(UndoAction.class));
         toolBar.add(RedoAction.get(RedoAction.class));
 
+        toolBar.addSeparator();
+        ButtonGroup interactionButtons = new ButtonGroup();
+
+        panModeAction = new PanModeAction();
+        panModeAction.setSelected(true);
+        button = new JToggleButton(panModeAction);
+        button.setSelected(true);
+        interactionButtons.add(button);
+        toolBar.add(button);
+        panModeAction.addPropertyChangeListener(this);
+
+        selectionModeAction = new SelectionModeAction();
+        button = new JToggleButton(selectionModeAction);
+        interactionButtons.add(button);
+        toolBar.add(button);
+        selectionModeAction.addPropertyChangeListener(this);
+
+        toolBar.add(Box.createHorizontalGlue());
+        Action action = Utilities.actionsForPath("QuickSearchShadow").get(0);
+        Component quicksearch = ((Presenter.Toolbar) action).getToolbarPresenter();
+        try {
+            // (aw) workaround for disappearing search bar due to reparenting one shared component instance.
+            quicksearch = (Component) quicksearch.getClass().getConstructor(KeyStroke.class).newInstance(new Object[]{null});
+        } catch (ReflectiveOperationException | IllegalArgumentException | SecurityException e) {
+        }
+        quicksearch.setMinimumSize(quicksearch.getPreferredSize()); // necessary for GTK LAF
+        toolBar.add(quicksearch);
+
         centerPanel = new JPanel();
         this.add(centerPanel, BorderLayout.CENTER);
         cardLayout = new CardLayout();
         centerPanel.setLayout(cardLayout);
-        centerPanel.add(SCENE_STRING, scene.getScrollPane());
+        centerPanel.add(SCENE_STRING, scene.getComponent());
         centerPanel.setBackground(Color.WHITE);
-        satelliteComponent = new ExtendedSatelliteComponent(scene);
+        satelliteComponent = scene.createSatelliteView();
         satelliteComponent.setSize(200, 200);
         centerPanel.add(SATELLITE_STRING, satelliteComponent);
 
-        CallbackSystemAction callFindAction = (CallbackSystemAction) SystemAction.get(FindAction.class);
-        NodeFindAction findAction = NodeFindAction.get(NodeFindAction.class);
-        Object key = callFindAction.getActionMapKey();
-        actionMap.put(key, findAction);
+        // TODO: Fix the hot key for entering the satellite view
+        this.addKeyListener(keyListener);
 
-        scene.getScrollPane().addKeyListener(keyListener);
-        scene.getView().addKeyListener(keyListener);
-        satelliteComponent.addKeyListener(keyListener);
+        scene.getComponent().addHierarchyBoundsListener(new HierarchyBoundsListener() {
 
-        scene.getScrollPane().addHierarchyBoundsListener(new HierarchyBoundsListener() {
-
+            @Override
             public void ancestorMoved(HierarchyEvent e) {
             }
 
+            @Override
             public void ancestorResized(HierarchyEvent e) {
-                if (!notFirstTime && scene.getScrollPane().getBounds().width > 0) {
+                if (!notFirstTime && scene.getComponent().getBounds().width > 0) {
                     notFirstTime = true;
                     SwingUtilities.invokeLater(new Runnable() {
 
+                        @Override
                         public void run() {
-                            Figure f = EditorTopComponent.this.scene.getModel().getDiagramToView().getRootFigure();
-                            if (f != null) {
-                                scene.setUndoRedoEnabled(false);
-                                scene.gotoFigure(f);
-                                scene.setUndoRedoEnabled(true);
-                            }
+                            EditorTopComponent.this.scene.initialize();
                         }
                     });
                 }
             }
         });
 
+        if (diagram.getGraph().getGroup().getGraphsCount() == 1) {
+            rangeSlider.setVisible(false);
+        }
+
         updateDisplayName();
     }
     private KeyListener keyListener = new KeyListener() {
 
+        @Override
         public void keyTyped(KeyEvent e) {
         }
 
+        @Override
         public void keyPressed(KeyEvent e) {
             if (e.getKeyCode() == KeyEvent.VK_S) {
                 EditorTopComponent.this.overviewButton.setSelected(true);
@@ -308,6 +346,7 @@
             }
         }
 
+        @Override
         public void keyReleased(KeyEvent e) {
             if (e.getKeyCode() == KeyEvent.VK_S) {
                 EditorTopComponent.this.overviewButton.setSelected(false);
@@ -317,7 +356,7 @@
     };
 
     public DiagramViewModel getDiagramModel() {
-        return scene.getModel();
+        return rangeSliderModel;
     }
 
     private void showSatellite() {
@@ -328,35 +367,15 @@
 
     private void showScene() {
         cardLayout.show(centerPanel, SCENE_STRING);
-        scene.getView().requestFocus();
-    }
-
-    public void findNode() {
-        findPanel.find();
+        scene.getComponent().requestFocus();
     }
 
     public void zoomOut() {
-        double zoom = scene.getZoomFactor();
-        Point viewPosition = scene.getScrollPane().getViewport().getViewPosition();
-        double newZoom = zoom / DiagramScene.ZOOM_INCREMENT;
-        if (newZoom > DiagramScene.ZOOM_MIN_FACTOR) {
-            scene.setZoomFactor(newZoom);
-            scene.validate();
-            scene.getScrollPane().getViewport().setViewPosition(new Point((int) (viewPosition.x / DiagramScene.ZOOM_INCREMENT), (int) (viewPosition.y / DiagramScene.ZOOM_INCREMENT)));
-            this.satelliteComponent.update();
-        }
+        scene.zoomOut();
     }
 
     public void zoomIn() {
-        double zoom = scene.getZoomFactor();
-        Point viewPosition = scene.getScrollPane().getViewport().getViewPosition();
-        double newZoom = zoom * DiagramScene.ZOOM_INCREMENT;
-        if (newZoom < DiagramScene.ZOOM_MAX_FACTOR) {
-            scene.setZoomFactor(newZoom);
-            scene.validate();
-            scene.getScrollPane().getViewport().setViewPosition(new Point((int) (viewPosition.x * DiagramScene.ZOOM_INCREMENT), (int) (viewPosition.y * DiagramScene.ZOOM_INCREMENT)));
-            this.satelliteComponent.update();
-        }
+        scene.zoomIn();
     }
 
     public void showPrevDiagram() {
@@ -370,11 +389,11 @@
     }
 
     public DiagramViewModel getModel() {
-        return scene.getModel();
+        return rangeSliderModel;
     }
 
     public FilterChain getFilterChain() {
-        return this.scene.getModel().getFilterChain();
+        return getModel().getFilterChain();
     }
 
     public static EditorTopComponent getActive() {
@@ -407,6 +426,7 @@
         // Variables declaration - do not modify//GEN-BEGIN:variables
         private javax.swing.JCheckBox jCheckBox1;
         // End of variables declaration//GEN-END:variables
+
     @Override
     public int getPersistenceType() {
         return TopComponent.PERSISTENCE_NEVER;
@@ -418,6 +438,7 @@
 
     @Override
     public void componentClosed() {
+        rangeSliderModel.close();
     }
 
     @Override
@@ -425,9 +446,18 @@
         return PREFERRED_ID;
     }
 
-    public void changed(RangeSliderModel model) {
-        updateDisplayName();
-    }
+    private ChangedListener<DiagramViewModel> diagramChangedListener = new ChangedListener<DiagramViewModel>() {
+
+        @Override
+        public void changed(DiagramViewModel source) {
+            updateDisplayName();
+            Collection<Object> list = new ArrayList<>();
+            list.add(new EditorInputGraphProvider(EditorTopComponent.this));
+            graphContent.set(list, null);
+            diagramProvider.getChangedEvent().fire();
+        }
+
+    };
 
     public boolean showPredSucc() {
         return (Boolean) predSuccAction.getValue(PredSuccAction.STATE);
@@ -435,24 +465,25 @@
 
     public void setSelection(PropertyMatcher matcher) {
 
-        Properties.PropertySelector<Figure> selector = new Properties.PropertySelector<Figure>(scene.getModel().getDiagramToView().getFigures());
+        Properties.PropertySelector<Figure> selector = new Properties.PropertySelector<>(getModel().getDiagramToView().getFigures());
         List<Figure> list = selector.selectMultiple(matcher);
-        boolean b = scene.getUndoRedoEnabled();
-        scene.setUndoRedoEnabled(false);
-        scene.gotoFigures(list);
-        scene.setUndoRedoEnabled(b);
+        setSelectedFigures(list);
+    }
+
+    public void setSelectedFigures(List<Figure> list) {
         scene.setSelection(list);
+        scene.centerFigures(list);
     }
 
     public void setSelectedNodes(Set<InputNode> nodes) {
 
-        List<Figure> list = new ArrayList<Figure>();
-        Set<Integer> ids = new HashSet<Integer>();
+        List<Figure> list = new ArrayList<>();
+        Set<Integer> ids = new HashSet<>();
         for (InputNode n : nodes) {
             ids.add(n.getId());
         }
 
-        for (Figure f : scene.getModel().getDiagramToView().getFigures()) {
+        for (Figure f : getModel().getDiagramToView().getFigures()) {
             for (InputNode n : f.getSource().getSourceNodes()) {
                 if (ids.contains(n.getId())) {
                     list.add(f);
@@ -461,10 +492,10 @@
             }
         }
 
-        scene.gotoFigures(list);
-        scene.setSelection(list);
+        setSelectedFigures(list);
     }
 
+    @Override
     public void propertyChange(PropertyChangeEvent evt) {
         if (evt.getSource() == this.predSuccAction) {
             boolean b = (Boolean) predSuccAction.getValue(PredSuccAction.STATE);
@@ -478,27 +509,35 @@
             }
         } else if (evt.getSource() == this.blockLayoutAction) {
             boolean b = (Boolean) blockLayoutAction.getValue(EnableBlockLayoutAction.STATE);
-            System.out.println("Showblocks = " + b);
             this.getModel().setShowBlocks(b);
+        } else if (evt.getSource() == this.hideDuplicatesAction) {
+            boolean b = (Boolean) hideDuplicatesAction.getValue(HideDuplicatesAction.STATE);
+            this.getModel().setHideDuplicates(b);
+        } else if (evt.getSource() == this.selectionModeAction || evt.getSource() == this.panModeAction) {
+            if (panModeAction.isSelected()) {
+                scene.setInteractionMode(DiagramViewer.InteractionMode.PANNING);
+            } else if (selectionModeAction.isSelected()) {
+                scene.setInteractionMode(DiagramViewer.InteractionMode.SELECTION);
+            }
         } else {
             assert false : "Unknown event source";
         }
     }
 
     public void extract() {
-        scene.showOnly(scene.getSelectedNodes());
+        getModel().showOnly(getModel().getSelectedNodes());
     }
 
     public void hideNodes() {
-        Set<Integer> selectedNodes = this.scene.getSelectedNodes();
-        HashSet<Integer> nodes = new HashSet<Integer>(scene.getModel().getHiddenNodes());
+        Set<Integer> selectedNodes = this.getModel().getSelectedNodes();
+        HashSet<Integer> nodes = new HashSet<>(getModel().getHiddenNodes());
         nodes.addAll(selectedNodes);
-        this.scene.showNot(nodes);
+        this.getModel().showNot(nodes);
     }
 
     public void expandPredecessors() {
-        Set<Figure> oldSelection = scene.getSelectedFigures();
-        Set<Figure> figures = new HashSet<Figure>();
+        Set<Figure> oldSelection = getModel().getSelectedFigures();
+        Set<Figure> figures = new HashSet<>();
 
         for (Figure f : this.getDiagramModel().getDiagramToView().getFigures()) {
             boolean ok = false;
@@ -518,12 +557,12 @@
             }
         }
 
-        scene.showAll(figures);
+        getModel().showAll(figures);
     }
 
     public void expandSuccessors() {
-        Set<Figure> oldSelection = scene.getSelectedFigures();
-        Set<Figure> figures = new HashSet<Figure>();
+        Set<Figure> oldSelection = getModel().getSelectedFigures();
+        Set<Figure> figures = new HashSet<>();
 
         for (Figure f : this.getDiagramModel().getDiagramToView().getFigures()) {
             boolean ok = false;
@@ -543,11 +582,11 @@
             }
         }
 
-        scene.showAll(figures);
+        getModel().showAll(figures);
     }
 
     public void showAll() {
-        scene.showNot(new HashSet<Integer>());
+        getModel().showNot(new HashSet<Integer>());
     }
 
     public Diagram getDiagram() {
@@ -555,23 +594,31 @@
     }
 
     @Override
-    protected void componentActivated() {
+    protected void componentHidden() {
+        super.componentHidden();
+        scene.componentHidden();
+
     }
 
     @Override
-    public void requestFocus() {
-        super.requestFocus();
-        scene.getView().requestFocus();
+    protected void componentShowing() {
+        super.componentShowing();
+        scene.componentShowing();
     }
 
     @Override
-    public boolean requestFocusInWindow() {
-        super.requestFocusInWindow();
-        return scene.getView().requestFocusInWindow();
+    public void requestActive() {
+        super.requestActive();
+        scene.getComponent().requestFocus();
     }
 
     @Override
     public UndoRedo getUndoRedo() {
         return scene.getUndoRedo();
     }
+
+    @Override
+    protected Object writeReplace() throws ObjectStreamException {
+        throw new NotSerializableException();
 }
+}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/ExportCookie.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/ExportCookie.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2007, 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
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/ExtendedPanAction.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,131 +0,0 @@
-/*
- * Copyright (c) 2008, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- *
- */
-package com.sun.hotspot.igv.view;
-
-import java.awt.Container;
-import java.awt.Dimension;
-import java.awt.Point;
-import org.netbeans.api.visual.widget.Scene;
-import org.netbeans.api.visual.widget.Widget;
-import org.netbeans.api.visual.action.WidgetAction;
-
-import java.awt.event.MouseEvent;
-import javax.swing.JComponent;
-import javax.swing.JScrollPane;
-import javax.swing.SwingUtilities;
-
-/**
- * @author David Kaspar
- * @author Thomas Wuerthinger
- */
-public class ExtendedPanAction extends WidgetAction.LockedAdapter {
-
-    private Scene scene;
-    private JScrollPane scrollPane;
-    private Point lastLocation;
-
-    protected boolean isLocked() {
-        return scrollPane != null;
-    }
-
-    @Override
-    public State mousePressed(Widget widget, WidgetMouseEvent event) {
-        if (event.getButton() == MouseEvent.BUTTON2 || event.getButton() == MouseEvent.BUTTON1 && ((event.getModifiers() & MouseEvent.CTRL_MASK) != 0)) {
-            scene = widget.getScene();
-            scrollPane = findScrollPane(scene.getView());
-            if (scrollPane != null) {
-                lastLocation = scene.convertSceneToView(widget.convertLocalToScene(event.getPoint()));
-                SwingUtilities.convertPointToScreen(lastLocation, scrollPane.getViewport().getView());
-                return State.createLocked(widget, this);
-            }
-        }
-        return State.REJECTED;
-    }
-
-    private JScrollPane findScrollPane(JComponent component) {
-        for (;;) {
-            if (component == null) {
-                return null;
-            }
-            if (component instanceof JScrollPane) {
-                return ((JScrollPane) component);
-            }
-            Container parent = component.getParent();
-            if (!(parent instanceof JComponent)) {
-                return null;
-            }
-            component = (JComponent) parent;
-        }
-    }
-
-    @Override
-    public State mouseReleased(Widget widget, WidgetMouseEvent event) {
-        boolean state = pan(widget, event.getPoint());
-        if (state) {
-            scrollPane = null;
-        }
-        return state ? State.createLocked(widget, this) : State.REJECTED;
-    }
-
-    @Override
-    public State mouseDragged(Widget widget, WidgetMouseEvent event) {
-        return pan(widget, event.getPoint()) ? State.createLocked(widget, this) : State.REJECTED;
-    }
-
-    private boolean pan(Widget widget, Point newLocation) {
-        if (scrollPane == null || scene != widget.getScene()) {
-            return false;
-        }
-        newLocation = scene.convertSceneToView(widget.convertLocalToScene(newLocation));
-        SwingUtilities.convertPointToScreen(newLocation, scrollPane.getViewport().getView());
-        Point viewPosition = scrollPane.getViewport().getViewPosition();
-        Dimension viewSize = scrollPane.getViewport().getViewSize();
-        Dimension viewPortSize = scrollPane.getViewport().getSize();
-
-        int xOffset = lastLocation.x - newLocation.x;
-        int yOffset = lastLocation.y - newLocation.y;
-
-        if (viewPortSize.height == viewSize.height) {
-            yOffset = 0;
-        }
-
-        if (viewPortSize.width == viewSize.width) {
-            xOffset = 0;
-        }
-
-        if (xOffset == 0 && yOffset == 0) {
-            return true;
-        }
-        viewPosition = new Point(viewPosition.x + xOffset, viewPosition.y + yOffset);
-        viewPosition.x = Math.max(viewPosition.x, 0);
-        viewPosition.y = Math.max(viewPosition.y, 0);
-        viewPosition.x = Math.min(viewPosition.x, scrollPane.getViewport().getView().getSize().width - scrollPane.getViewport().getSize().width);
-        viewPosition.y = Math.min(viewPosition.y, scrollPane.getViewport().getView().getSize().height - scrollPane.getViewport().getSize().height);
-
-        scrollPane.getViewport().setViewPosition(viewPosition);
-        scrollPane.getViewport().getView().repaint();
-        lastLocation = newLocation;
-        return true;
-    }
-}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/ExtendedSatelliteComponent.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/ExtendedSatelliteComponent.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,11 +23,10 @@
  */
 package com.sun.hotspot.igv.view;
 
-import org.netbeans.api.visual.widget.Scene;
-
-import javax.swing.*;
 import java.awt.*;
 import java.awt.event.*;
+import javax.swing.JComponent;
+import org.netbeans.api.visual.widget.Scene;
 
 /**
  * @author David Kaspar
@@ -48,6 +47,7 @@
         addMouseMotionListener(this);
     }
 
+    @Override
     public void addNotify() {
         super.addNotify();
         scene.addSceneListener(this);
@@ -59,6 +59,7 @@
         repaint();
     }
 
+    @Override
     public void removeNotify() {
         scene.getView().removeComponentListener(this);
         scene.removeSceneListener(this);
@@ -74,6 +75,7 @@
         }
     }
 
+    @Override
     public void paint(Graphics g) {
         Graphics2D gr = (Graphics2D) g;
         super.paint(g);
@@ -91,15 +93,15 @@
 
 
         if (image == null || vw != imageWidth || vh != imageHeight) {
-
             imageWidth = vw;
             imageHeight = vh;
             image = this.createImage(imageWidth, imageHeight);
             Graphics2D ig = (Graphics2D) image.getGraphics();
             ig.scale(scale, scale);
-            scene.setRealZoomFactor(scale);
+            double oldFactor = scene.getZoomFactor();
+            scene.setZoomFactor(scale);
             scene.paint(ig);
-            scene.setRealZoomFactor(0.0);
+            scene.setZoomFactor(oldFactor);
         }
 
         gr.drawImage(image, vx, vy, this);
@@ -121,27 +123,34 @@
         }
     }
 
+    @Override
     public void mouseClicked(MouseEvent e) {
     }
 
+    @Override
     public void mousePressed(MouseEvent e) {
         moveVisibleRect(e.getPoint());
     }
 
+    @Override
     public void mouseReleased(MouseEvent e) {
         moveVisibleRect(e.getPoint());
     }
 
+    @Override
     public void mouseEntered(MouseEvent e) {
     }
 
+    @Override
     public void mouseExited(MouseEvent e) {
     }
 
+    @Override
     public void mouseDragged(MouseEvent e) {
         moveVisibleRect(e.getPoint());
     }
 
+    @Override
     public void mouseMoved(MouseEvent e) {
     }
 
@@ -174,27 +183,34 @@
         this.repaint();
     }
 
+    @Override
     public void sceneRepaint() {
     //repaint ();
     }
 
+    @Override
     public void sceneValidating() {
     }
 
+    @Override
     public void sceneValidated() {
     }
 
+    @Override
     public void componentResized(ComponentEvent e) {
         repaint();
     }
 
+    @Override
     public void componentMoved(ComponentEvent e) {
         repaint();
     }
 
+    @Override
     public void componentShown(ComponentEvent e) {
     }
 
+    @Override
     public void componentHidden(ComponentEvent e) {
     }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/FindPanel.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,111 +0,0 @@
-/*
- * Copyright (c) 2008, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- *
- */
-package com.sun.hotspot.igv.view;
-
-import com.sun.hotspot.igv.graph.Figure;
-import com.sun.hotspot.igv.data.Properties;
-import com.sun.hotspot.igv.data.Properties.RegexpPropertyMatcher;
-import com.sun.hotspot.igv.data.Property;
-import java.awt.GridLayout;
-import java.awt.event.KeyEvent;
-import java.awt.event.KeyListener;
-import java.util.List;
-import java.util.SortedSet;
-import java.util.TreeSet;
-import javax.swing.JComboBox;
-import javax.swing.JPanel;
-import javax.swing.JTextField;
-
-/**
- *
- * @author Thomas Wuerthinger
- */
-class FindPanel extends JPanel implements KeyListener {
-
-    private JComboBox nameComboBox;
-    private JTextField valueTextField;
-
-    public FindPanel(List<Figure> figures) {
-        createDesign();
-        updateComboBox(figures);
-    }
-
-    protected void createDesign() {
-        setLayout(new GridLayout());
-        nameComboBox = new JComboBox();
-        valueTextField = new JTextField();
-        add(nameComboBox);
-        add(valueTextField);
-        valueTextField.addKeyListener(this);
-    }
-
-    public void updateComboBox(List<Figure> figures) {
-
-        String sel = (String) nameComboBox.getSelectedItem();
-        SortedSet<String> propertyNames = new TreeSet<String>();
-
-        for (Figure f : figures) {
-            Properties prop = f.getProperties();
-            for (Property p : prop) {
-                if (!propertyNames.contains(p.getName())) {
-                    propertyNames.add(p.getName());
-                }
-            }
-        }
-
-        for (String s : propertyNames) {
-            nameComboBox.addItem(s);
-        }
-        nameComboBox.setSelectedItem(sel);
-    }
-
-    public String getNameText() {
-        return (String) nameComboBox.getSelectedItem();
-    }
-
-    public String getValueText() {
-        return valueTextField.getText();
-    }
-
-    public void keyTyped(KeyEvent e) {
-    }
-
-    public void keyPressed(KeyEvent e) {
-        if (e.getKeyCode() == KeyEvent.VK_ENTER) {
-            find();
-        }
-    }
-
-    public void find() {
-        EditorTopComponent comp = EditorTopComponent.getActive();
-        if (comp != null) {
-            RegexpPropertyMatcher matcher = new RegexpPropertyMatcher(getNameText(), getValueText());
-            comp.setSelection(matcher);
-        }
-    }
-
-    public void keyReleased(KeyEvent e) {
-
-    }
-}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/GraphViewerImplementation.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/GraphViewerImplementation.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -27,6 +27,9 @@
 import com.sun.hotspot.igv.data.services.GraphViewer;
 import com.sun.hotspot.igv.graph.Diagram;
 import com.sun.hotspot.igv.settings.Settings;
+import org.openide.windows.Mode;
+import org.openide.windows.TopComponent;
+import org.openide.windows.WindowManager;
 
 /**
  *
@@ -34,7 +37,25 @@
  */
 public class GraphViewerImplementation implements GraphViewer {
 
-    public void view(InputGraph graph) {
+    @Override
+    public void view(InputGraph graph, boolean clone) {
+
+        if (!clone) {
+            WindowManager manager = WindowManager.getDefault();
+            for (Mode m : manager.getModes()) {
+                for (TopComponent t : manager.getOpenedTopComponents(m)) {
+                    if (t instanceof EditorTopComponent) {
+                        EditorTopComponent etc = (EditorTopComponent) t;
+                        if (etc.getModel().getGroup().getGraphs().contains(graph)) {
+                            etc.getModel().selectGraph(graph);
+                            t.requestActive();
+                            return;
+                        }
+                    }
+                }
+            }
+        }
+
         Diagram diagram = Diagram.createDiagram(graph, Settings.get().get(Settings.NODE_TEXT, Settings.NODE_TEXT_DEFAULT));
         EditorTopComponent tc = new EditorTopComponent(diagram);
         tc.open();
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/NodeQuickSearch.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,142 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+package com.sun.hotspot.igv.view;
+
+import com.sun.hotspot.igv.data.InputNode;
+import com.sun.hotspot.igv.data.Properties;
+import com.sun.hotspot.igv.data.Properties.RegexpPropertyMatcher;
+import com.sun.hotspot.igv.data.services.InputGraphProvider;
+import com.sun.hotspot.igv.util.LookupHistory;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
+import java.util.regex.Pattern;
+import org.netbeans.spi.quicksearch.SearchProvider;
+import org.netbeans.spi.quicksearch.SearchRequest;
+import org.netbeans.spi.quicksearch.SearchResponse;
+import org.openide.DialogDisplayer;
+import org.openide.NotifyDescriptor;
+import org.openide.NotifyDescriptor.Message;
+
+/**
+ *
+ * @author Thomas Wuerthinger
+ */
+public class NodeQuickSearch implements SearchProvider {
+
+    private static final String DEFAULT_PROPERTY = "name";
+
+    /**
+     * Method is called by infrastructure when search operation was requested.
+     * Implementors should evaluate given request and fill response object with
+     * apropriate results
+     *
+     * @param request Search request object that contains information what to search for
+     * @param response Search response object that stores search results. Note that it's important to react to return value of SearchResponse.addResult(...) method and stop computation if false value is returned.
+     */
+    @Override
+    public void evaluate(SearchRequest request, SearchResponse response) {
+        String query = request.getText();
+        if (query.trim().isEmpty()) {
+            return;
+        }
+
+        final String[] parts = query.split("=", 2);
+
+        String name;
+        String value;
+
+        if (parts.length == 1) {
+            name = DEFAULT_PROPERTY;
+            value = ".*" + Pattern.quote(parts[0]) + ".*";
+        } else {
+            name = parts[0];
+            value = parts[1];
+        }
+
+        if (value.isEmpty()) {
+            value = ".*";
+        }
+
+        final InputGraphProvider p = LookupHistory.getLast(InputGraphProvider.class);
+        if (p != null && p.getGraph() != null) {
+            List<InputNode> matches = null;
+            try {
+                RegexpPropertyMatcher matcher = new RegexpPropertyMatcher(name, value, Pattern.CASE_INSENSITIVE);
+                Properties.PropertySelector<InputNode> selector = new Properties.PropertySelector<>(p.getGraph().getNodes());
+
+                matches = selector.selectMultiple(matcher);
+            } catch (Exception e) {
+                final String msg = e.getMessage();
+                response.addResult(new Runnable() {
+                    @Override
+                        public void run() {
+                            Message desc = new NotifyDescriptor.Message("An exception occurred during the search, "
+                                    + "perhaps due to a malformed query string:\n" + msg,
+                                    NotifyDescriptor.WARNING_MESSAGE);
+                            DialogDisplayer.getDefault().notify(desc);
+                        }
+                    },
+                    "(Error during search)"
+                );
+            }
+
+            if (matches != null) {
+                final Set<InputNode> set = new HashSet<>(matches);
+                response.addResult(new Runnable() {
+                    @Override
+                        public void run() {
+                            final EditorTopComponent comp = EditorTopComponent.getActive();
+                            if (comp != null) {
+                                comp.setSelectedNodes(set);
+                                comp.requestActive();
+                            }
+                        }
+                    },
+                    "All " + matches.size() + " matching nodes (" + name + "=" + value + ")"
+                );
+
+                // Single matches
+                for (final InputNode n : matches) {
+                    response.addResult(new Runnable() {
+                        @Override
+                            public void run() {
+                                final EditorTopComponent comp = EditorTopComponent.getActive();
+                                if (comp != null) {
+                                    final Set<InputNode> tmpSet = new HashSet<>();
+                                    tmpSet.add(n);
+                                    comp.setSelectedNodes(tmpSet);
+                                    comp.requestActive();
+                                }
+                            }
+                        },
+                        n.getProperties().get(name) + " (" + n.getId() + " " + n.getProperties().get("name") + ")"
+                    );
+                }
+            }
+        } else {
+            System.out.println("no input graph provider!");
+        }
+    }
+}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/PreferenceConstants.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,34 +0,0 @@
-/*
- * Copyright (c) 2008, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- *
- */
-package com.sun.hotspot.igv.view;
-
-/**
- *
- * @author Thomas Wuerthinger
- */
-public class PreferenceConstants {
-
-    public static final String KEY_LINE_GENERATOR = "lineGenerator";
-    public static final String DEFAULT_LINE_GENERATOR = "com.sun.hotspot.igv.positioning.BasicLineGenerator";
-}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/SlotLayout.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,171 +0,0 @@
-/*
- * Copyright (c) 2008, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- *
- */
-package com.sun.hotspot.igv.view;
-
-import java.awt.Point;
-import java.awt.Rectangle;
-import java.util.Collection;
-import java.util.List;
-import org.netbeans.api.visual.layout.Layout;
-import org.netbeans.api.visual.layout.LayoutFactory;
-import org.netbeans.api.visual.widget.Widget;
-
-/**
- *
- * @author Thomas Wuerthinger
- */
-public class SlotLayout implements Layout {
-
-    public enum HorizontalAlignment {
-
-        Left,
-        Center,
-        Right
-    }
-    private Layout baseLayout;
-    private HorizontalAlignment alignment;
-    private boolean vertical;
-
-    public SlotLayout() {
-        this(HorizontalAlignment.Center, false);
-    }
-
-    public SlotLayout(HorizontalAlignment alignment, boolean vertical) {
-        this.alignment = alignment;
-        baseLayout = LayoutFactory.createVerticalFlowLayout();
-        this.vertical = vertical;
-    }
-
-    public void layout(Widget widget) {
-        if (!vertical) {
-            Collection<Widget> children = widget.getChildren();
-            int gap = 0;
-            int max = 0;
-            for (Widget child : children) {
-                Rectangle preferredBounds = child.getPreferredBounds();
-                int i = preferredBounds.width;
-                if (i > max) {
-                    max = i;
-                }
-            }
-            int pos = 0;
-            for (Widget child : children) {
-                Rectangle preferredBounds = child.getPreferredBounds();
-                int x = preferredBounds.x;
-                int y = preferredBounds.y;
-                int width = preferredBounds.width;
-                int height = preferredBounds.height;
-                if (pos == 0) {
-                    pos += height / 2;
-                }
-                int lx = -x;
-                int ly = pos - y;
-                switch (alignment) {
-                    case Center:
-                        lx += (max - width) / 2;
-                        break;
-                    case Left:
-                        break;
-                    case Right:
-                        lx += max - width;
-                        break;
-                }
-                child.resolveBounds(new Point(lx, ly), new Rectangle(x, y, width, height));
-                pos += height + gap;
-            }
-        } else {
-
-            Collection<Widget> children = widget.getChildren();
-            int gap = 0;
-            int max = 0;
-            for (Widget child : children) {
-                Rectangle preferredBounds = child.getPreferredBounds();
-                int i = preferredBounds.height;
-                if (i > max) {
-                    max = i;
-                }
-            }
-            int pos = 0;
-            for (Widget child : children) {
-                Rectangle preferredBounds = child.getPreferredBounds();
-                int x = preferredBounds.x;
-                int y = preferredBounds.y;
-                int width = preferredBounds.width;
-                int height = preferredBounds.height;
-                if (pos == 0) {
-                    pos += width / 2;
-                }
-                int lx = pos - x;
-                int ly = -y;
-                switch (alignment) {
-                    case Center:
-                        ly += (max - height) / 2;
-                        break;
-                    case Left:
-                        break;
-                    case Right:
-                        ly += max - height;
-                        break;
-                }
-                child.resolveBounds(new Point(lx, ly), new Rectangle(x, y, width, height));
-                pos += width + gap;
-            }
-
-        }
-    }
-
-    public boolean requiresJustification(Widget widget) {
-        return true;
-    }
-
-    public void justify(Widget widget) {
-        baseLayout.justify(widget);
-
-        Rectangle client = widget.getClientArea();
-        List<Widget> children = widget.getChildren();
-
-        int count = children.size();
-        int z = 0;
-
-        int maxWidth = 0;
-        for (Widget c : children) {
-            if (c.getPreferredBounds().width > maxWidth) {
-                maxWidth = c.getPreferredBounds().width;
-            }
-        }
-
-        for (Widget c : children) {
-            z++;
-            Point curLocation = c.getLocation();
-            Rectangle curBounds = c.getBounds();
-
-
-            Point location = new Point(curLocation.x, client.y + client.height * z / (count + 1) - curBounds.height / 2);
-            if (vertical) {
-                location = new Point(client.x + client.width * z / (count + 1) - maxWidth / 2, curLocation.y);
-            }
-            c.resolveBounds(location, null);
-        }
-    }
-}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/Bundle.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/Bundle.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,7 +1,6 @@
 CTL_EditorAction=Open Editor Window
-CTL_LineGeneratorAction=Line Generator
 CTL_NextDiagramAction=Show next graph
 CTL_EnableBlockLayoutAction=Enable block layout
 CTL_NodeFindAction=Find
 CTL_PrevDiagramAction=Show previous graph
-CTL_ExportAction=Export...
+CTL_ExportAction=Export current graph...
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/CustomizablePanAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,146 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright (c) 1997, 2015, Oracle and/or its affiliates. All rights reserved.
+ *
+ * Oracle and Java are registered trademarks of Oracle and/or its affiliates.
+ * Other names may be trademarks of their respective owners.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common
+ * Development and Distribution License("CDDL") (collectively, the
+ * "License"). You may not use this file except in compliance with the
+ * License. You can obtain a copy of the License at
+ * http://www.netbeans.org/cddl-gplv2.html
+ * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
+ * specific language governing permissions and limitations under the
+ * License.  When distributing the software, include this License Header
+ * Notice in each file and include the License file at
+ * nbbuild/licenses/CDDL-GPL-2-CP.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the GPL Version 2 section of the License file that
+ * accompanied this code. If applicable, add the following below the
+ * License Header, with the fields enclosed by brackets [] replaced by
+ * your own identifying information:
+ * "Portions Copyrighted [year] [name of copyright owner]"
+ *
+ * Contributor(s):
+ *
+ * The Original Software is NetBeans. The Initial Developer of the Original
+ * Software is Sun Microsystems, Inc. Portions Copyright 1997-2007 Sun
+ * Microsystems, Inc. All Rights Reserved.
+ *
+ * If you wish your version of this file to be governed by only the CDDL
+ * or only the GPL Version 2, indicate your decision by adding
+ * "[Contributor] elects to include this software in this distribution
+ * under the [CDDL or GPL Version 2] license." If you do not indicate a
+ * single choice of license, a recipient has the option to distribute
+ * your version of this file under either the CDDL, the GPL Version 2 or
+ * to extend the choice of license to its licensees as provided above.
+ * However, if you add GPL Version 2 code and therefore, elected the GPL
+ * Version 2 license, then the option applies only if the new code is
+ * made subject to such option by the copyright holder.
+ */
+package com.sun.hotspot.igv.view.actions;
+
+import java.awt.Container;
+import java.awt.Point;
+import java.awt.Rectangle;
+import javax.swing.JComponent;
+import javax.swing.JScrollPane;
+import javax.swing.SwingUtilities;
+import org.netbeans.api.visual.action.WidgetAction;
+import org.netbeans.api.visual.action.WidgetAction.State;
+import org.netbeans.api.visual.action.WidgetAction.WidgetMouseEvent;
+import org.netbeans.api.visual.widget.Scene;
+import org.netbeans.api.visual.widget.Widget;
+
+/**
+ * @author David Kaspar
+ * @author Peter Hofer
+ */
+public class CustomizablePanAction extends WidgetAction.LockedAdapter {
+    private boolean enabled = true;
+
+    private Scene scene;
+    private JScrollPane scrollPane;
+    private Point lastLocation;
+
+    private final int modifiersExMask;
+    private final int modifiersEx;
+
+    public CustomizablePanAction(int modifiersExMask, int modifiersEx) {
+        this.modifiersExMask = modifiersExMask;
+        this.modifiersEx = modifiersEx;
+    }
+
+    @Override
+    protected boolean isLocked() {
+        return scrollPane != null;
+    }
+
+    public void setEnabled(boolean enabled) {
+        if (this.enabled != enabled) {
+            if (isLocked())
+                throw new IllegalStateException();
+
+            this.enabled = enabled;
+        }
+    }
+
+    @Override
+    public State mousePressed (Widget widget, WidgetMouseEvent event) {
+        if (isLocked ())
+            return State.createLocked (widget, this);
+        if (enabled && (event.getModifiersEx() & modifiersExMask) == modifiersEx) {
+            scene = widget.getScene ();
+            scrollPane = findScrollPane (scene.getView ());
+            if (scrollPane != null) {
+                lastLocation = scene.convertSceneToView (widget.convertLocalToScene (event.getPoint ()));
+                SwingUtilities.convertPointToScreen (lastLocation, scene.getView ());
+                return State.createLocked (widget, this);
+            }
+        }
+        return State.REJECTED;
+    }
+
+    private JScrollPane findScrollPane (JComponent component) {
+        for (;;) {
+            if (component == null)
+                return null;
+            if (component instanceof JScrollPane)
+                return ((JScrollPane) component);
+            Container parent = component.getParent ();
+            if (! (parent instanceof JComponent))
+                return null;
+            component = (JComponent) parent;
+        }
+    }
+
+    @Override
+    public State mouseReleased (Widget widget, WidgetMouseEvent event) {
+        boolean state = pan (widget, event.getPoint ());
+        if (state)
+            scrollPane = null;
+        return state ? State.createLocked (widget, this) : State.REJECTED;
+    }
+
+    @Override
+    public State mouseDragged (Widget widget, WidgetMouseEvent event) {
+        return pan (widget, event.getPoint ()) ? State.createLocked (widget, this) : State.REJECTED;
+    }
+
+    private boolean pan (Widget widget, Point newLocation) {
+        if (scrollPane == null  ||  scene != widget.getScene ())
+            return false;
+        newLocation = scene.convertSceneToView (widget.convertLocalToScene (newLocation));
+        SwingUtilities.convertPointToScreen (newLocation, scene.getView ());
+        JComponent view = scene.getView ();
+        Rectangle rectangle = view.getVisibleRect ();
+        rectangle.x += lastLocation.x - newLocation.x;
+        rectangle.y += lastLocation.y - newLocation.y;
+        view.scrollRectToVisible (rectangle);
+        lastLocation = newLocation;
+        return true;
+    }
+}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/EnableBlockLayoutAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/EnableBlockLayoutAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -27,6 +27,7 @@
 import javax.swing.AbstractAction;
 import javax.swing.Action;
 import javax.swing.ImageIcon;
+import org.openide.util.ImageUtilities;
 
 /**
  *
@@ -38,9 +39,9 @@
     public static final String STATE = "state";
 
     public EnableBlockLayoutAction() {
-        state = true;
-        putValue(AbstractAction.SMALL_ICON, new ImageIcon(org.openide.util.Utilities.loadImage(iconResource())));
-        putValue(STATE, true);
+        state = false;
+        putValue(AbstractAction.SMALL_ICON, new ImageIcon(ImageUtilities.loadImage(iconResource())));
+        putValue(STATE, state);
         putValue(Action.SHORT_DESCRIPTION, "Cluster nodes into blocks");
     }
 
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/ExpandPredecessorsAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/ExpandPredecessorsAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -33,6 +33,7 @@
  */
 public final class ExpandPredecessorsAction extends CallableSystemAction {
 
+    @Override
     public void performAction() {
         EditorTopComponent editor = EditorTopComponent.getActive();
         if (editor != null) {
@@ -40,8 +41,9 @@
         }
     }
 
+    @Override
     public String getName() {
-        return "Expand Predecessors";
+        return "Expand Above";
     }
 
     @Override
@@ -49,6 +51,7 @@
         super.initialize();
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/ExpandSuccessorsAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/ExpandSuccessorsAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -33,6 +33,7 @@
  */
 public final class ExpandSuccessorsAction extends CallableSystemAction {
 
+    @Override
     public void performAction() {
         EditorTopComponent editor = EditorTopComponent.getActive();
         if (editor != null) {
@@ -40,8 +41,9 @@
         }
     }
 
+    @Override
     public String getName() {
-        return "Expand Successors";
+        return "Expand Below";
     }
 
     @Override
@@ -49,6 +51,7 @@
         super.initialize();
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/ExportAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/ExportAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -32,12 +32,7 @@
 import javax.swing.JFileChooser;
 import javax.swing.KeyStroke;
 import javax.swing.filechooser.FileFilter;
-import org.openide.util.HelpCtx;
-import org.openide.util.Lookup;
-import org.openide.util.LookupEvent;
-import org.openide.util.LookupListener;
-import org.openide.util.NbBundle;
-import org.openide.util.Utilities;
+import org.openide.util.*;
 import org.openide.util.actions.CallableSystemAction;
 
 /**
@@ -50,27 +45,31 @@
     private final Lookup.Result<ExportCookie> result;
 
     public ExportAction() {
-        putValue(Action.SHORT_DESCRIPTION, "Export current graph as an SVG file");
+        putValue(Action.SHORT_DESCRIPTION, "Export current graph as SVG file");
         putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_E, InputEvent.CTRL_MASK));
         lookup = Utilities.actionsGlobalContext();
-        result = lookup.lookup(new Lookup.Template<ExportCookie>(ExportCookie.class));
+        result = lookup.lookup(new Lookup.Template<>(ExportCookie.class));
         result.addLookupListener(this);
         resultChanged(null);
     }
 
+    @Override
     public void resultChanged(LookupEvent e) {
         super.setEnabled(result.allInstances().size() > 0);
     }
 
+    @Override
     public void performAction() {
 
         JFileChooser fc = new JFileChooser();
         fc.setFileFilter(new FileFilter() {
 
+            @Override
             public boolean accept(File f) {
                 return true;
             }
 
+            @Override
             public String getDescription() {
                 return "SVG files (*.svg)";
             }
@@ -97,15 +96,17 @@
         }
     }
 
+    @Override
     public String getName() {
         return NbBundle.getMessage(ExportAction.class, "CTL_ExportAction");
     }
 
     @Override
     protected String iconResource() {
-        return "com/sun/hotspot/igv/view/images/export.gif";
+        return "com/sun/hotspot/igv/view/images/export.png";
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/ExtractAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/ExtractAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -37,6 +37,7 @@
  */
 public final class ExtractAction extends CallableSystemAction {
 
+    @Override
     public void performAction() {
         EditorTopComponent editor = EditorTopComponent.getActive();
         if (editor != null) {
@@ -49,6 +50,7 @@
         putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_X, Event.CTRL_MASK, false));
     }
 
+    @Override
     public String getName() {
         return "Extract action";
     }
@@ -58,6 +60,7 @@
         super.initialize();
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/HideAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/HideAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -37,6 +37,7 @@
  */
 public final class HideAction extends CallableSystemAction {
 
+    @Override
     public void performAction() {
         EditorTopComponent editor = EditorTopComponent.getActive();
         if (editor != null) {
@@ -49,6 +50,7 @@
         putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_H, Event.CTRL_MASK, false));
     }
 
+    @Override
     public String getName() {
         return "Hide";
     }
@@ -58,6 +60,7 @@
         super.initialize();
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/HideDuplicatesAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,60 @@
+/*
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+package com.sun.hotspot.igv.view.actions;
+
+import java.awt.event.ActionEvent;
+import javax.swing.AbstractAction;
+import javax.swing.Action;
+import javax.swing.ImageIcon;
+import org.openide.util.ImageUtilities;
+
+/**
+ *
+ * @author Tom Rodriguez
+ */
+public class HideDuplicatesAction extends AbstractAction {
+
+    private boolean state;
+    public static final String STATE = "state";
+
+    public HideDuplicatesAction() {
+        putValue(AbstractAction.SMALL_ICON, new ImageIcon(ImageUtilities.loadImage(iconResource())));
+        putValue(Action.SHORT_DESCRIPTION, "Hide graphs which are the same as the previous graph");
+        setState(false);
+    }
+
+    @Override
+    public void actionPerformed(ActionEvent ev) {
+        setState(!state);
+    }
+
+    public void setState(boolean b) {
+        this.putValue(STATE, b);
+        this.state = b;
+    }
+
+    protected String iconResource() {
+        return "com/sun/hotspot/igv/view/images/hideDuplicates.png";
+    }
+}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/MouseOverAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/MouseOverAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/NextDiagramAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/NextDiagramAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,15 +23,12 @@
  */
 package com.sun.hotspot.igv.view.actions;
 
-import com.sun.hotspot.igv.view.DiagramViewModel;
 import com.sun.hotspot.igv.data.ChangedListener;
 import com.sun.hotspot.igv.util.ContextAction;
+import com.sun.hotspot.igv.view.DiagramViewModel;
 import javax.swing.Action;
 import javax.swing.ImageIcon;
-import org.openide.util.HelpCtx;
-import org.openide.util.Lookup;
-import org.openide.util.NbBundle;
-import org.openide.util.Utilities;
+import org.openide.util.*;
 
 /**
  *
@@ -47,13 +44,15 @@
 
     public NextDiagramAction(Lookup lookup) {
         putValue(Action.SHORT_DESCRIPTION, "Show next graph of current group");
-        putValue(Action.SMALL_ICON, new ImageIcon(Utilities.loadImage("com/sun/hotspot/igv/view/images/next_diagram.png")));
+        putValue(Action.SMALL_ICON, new ImageIcon(ImageUtilities.loadImage("com/sun/hotspot/igv/view/images/next_diagram.png")));
     }
 
+    @Override
     public String getName() {
         return NbBundle.getMessage(NextDiagramAction.class, "CTL_NextDiagramAction");
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
@@ -95,10 +94,12 @@
         return model.getSecondPosition() != model.getPositions().size() - 1;
     }
 
+    @Override
     public Action createContextAwareInstance(Lookup arg0) {
         return new NextDiagramAction(arg0);
     }
 
+    @Override
     public void changed(DiagramViewModel source) {
         update(source);
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/NodeFindAction.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,71 +0,0 @@
-/*
- * Copyright (c) 2008, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- *
- */
-package com.sun.hotspot.igv.view.actions;
-
-import com.sun.hotspot.igv.view.EditorTopComponent;
-import javax.swing.Action;
-import org.openide.util.HelpCtx;
-import org.openide.util.NbBundle;
-import org.openide.util.actions.CallableSystemAction;
-
-/**
- *
- * @author Thomas Wuerthinger
- */
-public final class NodeFindAction extends CallableSystemAction {
-
-    public void performAction() {
-        EditorTopComponent comp = EditorTopComponent.getActive();
-        if (comp != null) {
-            comp.findNode();
-        }
-    }
-
-    public NodeFindAction() {
-        putValue(Action.SHORT_DESCRIPTION, "Find nodes");
-    }
-
-    public String getName() {
-        return NbBundle.getMessage(NodeFindAction.class, "CTL_NodeFindAction");
-    }
-
-    public HelpCtx getHelpCtx() {
-        return HelpCtx.DEFAULT_HELP;
-    }
-
-    @Override
-    protected boolean asynchronous() {
-        return false;
-    }
-
-    @Override
-    public boolean isEnabled() {
-        return true;
-    }
-
-    @Override
-    protected String iconResource() {
-        return "com/sun/hotspot/igv/view/images/search.gif";
-    }
-}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/OverviewAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/OverviewAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -27,6 +27,7 @@
 import javax.swing.AbstractAction;
 import javax.swing.Action;
 import javax.swing.ImageIcon;
+import org.openide.util.ImageUtilities;
 
 /**
  *
@@ -38,11 +39,12 @@
     public static final String STATE = "state";
 
     public OverviewAction() {
-        putValue(AbstractAction.SMALL_ICON, new ImageIcon(org.openide.util.Utilities.loadImage(iconResource())));
+        putValue(AbstractAction.SMALL_ICON, new ImageIcon(ImageUtilities.loadImage(iconResource())));
         putValue(Action.SHORT_DESCRIPTION, "Show satellite view of whole graph");
         setState(false);
     }
 
+    @Override
     public void actionPerformed(ActionEvent ev) {
         setState(!state);
     }
@@ -53,6 +55,6 @@
     }
 
     protected String iconResource() {
-        return "com/sun/hotspot/igv/view/images/overview.gif";
+        return "com/sun/hotspot/igv/view/images/overview.png";
     }
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/PanModeAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,59 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+package com.sun.hotspot.igv.view.actions;
+
+import java.awt.event.ActionEvent;
+import javax.swing.AbstractAction;
+import javax.swing.Action;
+import javax.swing.ImageIcon;
+import org.openide.util.ImageUtilities;
+
+public class PanModeAction extends AbstractAction {
+
+    private boolean state;
+
+    public PanModeAction() {
+        putValue(AbstractAction.SMALL_ICON, new ImageIcon(ImageUtilities.loadImage(iconResource())));
+        putValue(SELECTED_KEY, false);
+        putValue(Action.SHORT_DESCRIPTION, "Panning mode");
+    }
+
+    public boolean isSelected() {
+        return (Boolean)getValue(SELECTED_KEY);
+    }
+
+    public void setSelected(boolean b) {
+        if (isSelected() != b) {
+            this.putValue(SELECTED_KEY, b);
+        }
+    }
+
+    protected String iconResource() {
+        return "com/sun/hotspot/igv/view/images/pan_mode.png";
+    }
+
+    @Override
+    public void actionPerformed(ActionEvent e) {
+    }
+}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/PredSuccAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/PredSuccAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -27,6 +27,7 @@
 import javax.swing.AbstractAction;
 import javax.swing.Action;
 import javax.swing.ImageIcon;
+import org.openide.util.ImageUtilities;
 
 /**
  *
@@ -39,11 +40,12 @@
 
     public PredSuccAction() {
         state = true;
-        putValue(AbstractAction.SMALL_ICON, new ImageIcon(org.openide.util.Utilities.loadImage(iconResource())));
+        putValue(AbstractAction.SMALL_ICON, new ImageIcon(ImageUtilities.loadImage(iconResource())));
         putValue(STATE, true);
         putValue(Action.SHORT_DESCRIPTION, "Show neighboring nodes of fully visible nodes semi-transparent");
     }
 
+    @Override
     public void actionPerformed(ActionEvent ev) {
         this.state = !state;
         this.putValue(STATE, state);
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/PrevDiagramAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/PrevDiagramAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -24,14 +24,11 @@
 package com.sun.hotspot.igv.view.actions;
 
 import com.sun.hotspot.igv.data.ChangedListener;
+import com.sun.hotspot.igv.util.ContextAction;
 import com.sun.hotspot.igv.view.DiagramViewModel;
-import com.sun.hotspot.igv.util.ContextAction;
 import javax.swing.Action;
 import javax.swing.ImageIcon;
-import org.openide.util.HelpCtx;
-import org.openide.util.Lookup;
-import org.openide.util.NbBundle;
-import org.openide.util.Utilities;
+import org.openide.util.*;
 
 /**
  *
@@ -47,13 +44,15 @@
 
     public PrevDiagramAction(Lookup lookup) {
         putValue(Action.SHORT_DESCRIPTION, "Show previous graph of current group");
-        putValue(Action.SMALL_ICON, new ImageIcon(Utilities.loadImage("com/sun/hotspot/igv/view/images/prev_diagram.png")));
+        putValue(Action.SMALL_ICON, new ImageIcon(ImageUtilities.loadImage("com/sun/hotspot/igv/view/images/prev_diagram.png")));
     }
 
+    @Override
     public String getName() {
         return NbBundle.getMessage(PrevDiagramAction.class, "CTL_PrevDiagramAction");
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
@@ -95,10 +94,12 @@
         return model.getFirstPosition() != 0;
     }
 
+    @Override
     public Action createContextAwareInstance(Lookup arg0) {
         return new PrevDiagramAction(arg0);
     }
 
+    @Override
     public void changed(DiagramViewModel source) {
         update(source);
     }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/SelectionModeAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,57 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+package com.sun.hotspot.igv.view.actions;
+
+import java.awt.event.ActionEvent;
+import javax.swing.AbstractAction;
+import javax.swing.Action;
+import javax.swing.ImageIcon;
+import org.openide.util.ImageUtilities;
+
+public class SelectionModeAction extends AbstractAction {
+
+    public SelectionModeAction() {
+        putValue(AbstractAction.SMALL_ICON, new ImageIcon(ImageUtilities.loadImage(iconResource())));
+        putValue(SELECTED_KEY, false);
+        putValue(Action.SHORT_DESCRIPTION, "Selection mode");
+    }
+
+    public boolean isSelected() {
+        return (Boolean)getValue(SELECTED_KEY);
+    }
+
+    public void setSelected(boolean b) {
+        if (isSelected() != b) {
+            this.putValue(SELECTED_KEY, b);
+        }
+    }
+
+    protected String iconResource() {
+        return "com/sun/hotspot/igv/view/images/selection_mode.png";
+    }
+
+    @Override
+    public void actionPerformed(ActionEvent e) {
+    }
+}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/ShowAllAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/ShowAllAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,7 +23,7 @@
  */
 package com.sun.hotspot.igv.view.actions;
 
-import com.sun.hotspot.igv.view.*;
+import com.sun.hotspot.igv.view.EditorTopComponent;
 import java.awt.event.InputEvent;
 import java.awt.event.KeyEvent;
 import javax.swing.Action;
@@ -37,6 +37,7 @@
  */
 public final class ShowAllAction extends CallableSystemAction {
 
+    @Override
     public void performAction() {
         EditorTopComponent editor = EditorTopComponent.getActive();
         if (editor != null) {
@@ -49,6 +50,7 @@
         putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_A, InputEvent.CTRL_MASK));
     }
 
+    @Override
     public String getName() {
         return "Show all";
     }
@@ -58,6 +60,7 @@
         super.initialize();
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/ZoomInAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/ZoomInAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -37,6 +37,7 @@
  */
 public final class ZoomInAction extends CallableSystemAction {
 
+    @Override
     public void performAction() {
         EditorTopComponent editor = EditorTopComponent.getActive();
         if (editor != null) {
@@ -44,6 +45,7 @@
         }
     }
 
+    @Override
     public String getName() {
         return "Zoom in";
     }
@@ -53,6 +55,7 @@
         putValue(Action.SHORT_DESCRIPTION, "Zoom in");
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
@@ -64,6 +67,6 @@
 
     @Override
     protected String iconResource() {
-        return "com/sun/hotspot/igv/view/images/zoomin.gif";
+        return "com/sun/hotspot/igv/view/images/zoom_in.png";
     }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/ZoomOutAction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/actions/ZoomOutAction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -37,6 +37,7 @@
  */
 public final class ZoomOutAction extends CallableSystemAction {
 
+    @Override
     public void performAction() {
         EditorTopComponent editor = EditorTopComponent.getActive();
         if (editor != null) {
@@ -50,6 +51,7 @@
         putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_MINUS, Event.CTRL_MASK, false));
     }
 
+    @Override
     public String getName() {
         return "Zoom out";
     }
@@ -59,6 +61,7 @@
         super.initialize();
     }
 
+    @Override
     public HelpCtx getHelpCtx() {
         return HelpCtx.DEFAULT_HELP;
     }
@@ -70,6 +73,6 @@
 
     @Override
     protected String iconResource() {
-        return "com/sun/hotspot/igv/view/images/zoomout.gif";
+        return "com/sun/hotspot/igv/view/images/zoom_out.png";
     }
 }
Binary file hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/images/export.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/images/export.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/images/hideDuplicates.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/images/overview.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/images/overview.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/images/pan_mode.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/images/search.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/images/selection_mode.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/images/zoom_in.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/images/zoom_out.png has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/images/zoomin.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/images/zoomout.gif has changed
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/layer.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/layer.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -24,36 +24,65 @@
         <folder name="View">
             <file name="com-sun-hotspot-igv-view-actions-PrevDiagramAction.shadow">
                 <attr name="originalFile" stringvalue="Actions/View/com-sun-hotspot-igv-view-actions-PrevDiagramAction.instance"/>
+                <attr name="position" intvalue="100"/>
             </file>
             <file name="com-sun-hotspot-igv-view-actions-NextDiagramAction.shadow">
                 <attr name="originalFile" stringvalue="Actions/View/com-sun-hotspot-igv-view-actions-NextDiagramAction.instance"/>
+                <attr name="position" intvalue="150"/>
             </file>
             <file name="com-sun-hotspot-igv-view-actions-ShowAllAction.shadow">
                 <attr name="originalFile" stringvalue="Actions/View/com-sun-hotspot-igv-view-actions-ShowAllAction.instance"/>
+                <attr name="position" intvalue="200"/>
             </file>
             <file name="com-sun-hotspot-igv-view-actions-ExtractAction.shadow">
                 <attr name="originalFile" stringvalue="Actions/View/com-sun-hotspot-igv-view-actions-ExtractAction.instance"/>
+                <attr name="position" intvalue="300"/>
             </file>
             <file name="com-sun-hotspot-igv-view-actions-HideAction.shadow">
                 <attr name="originalFile" stringvalue="Actions/View/com-sun-hotspot-igv-view-actions-HideAction.instance"/>
+                <attr name="position" intvalue="400"/>
             </file>
             <file name="com-sun-hotspot-igv-view-actions-ZoomInAction.shadow">
                 <attr name="originalFile" stringvalue="Actions/View/com-sun-hotspot-igv-view-actions-ZoomInAction.instance"/>
+                <attr name="position" intvalue="500"/>
             </file>
             <file name="com-sun-hotspot-igv-view-actions-ZoomOutAction.shadow">
                 <attr name="originalFile" stringvalue="Actions/View/com-sun-hotspot-igv-view-actions-ZoomOutAction.instance"/>
+                <attr name="position" intvalue="550"/>
             </file>
         </folder>
         <folder name="File">
+            <file name="ExportActionSeparator.instance">
+                <attr name="instanceClass" stringvalue="javax.swing.JSeparator"/>
+                <attr name="position" intvalue="700"/>
+            </file>
             <file name="com-sun-hotspot-igv-view-actions-ExportAction.shadow">
                 <attr name="originalFile" stringvalue="Actions/File/com-sun-hotspot-igv-view-actions-ExportAction.instance"/>
-                <attr name="position" intvalue="600"/>
+                <attr name="position" intvalue="710"/>
             </file>
         </folder>
     </folder>
-    <folder name="Toolbars">
-        <folder name="Edit">
-            <attr name="com-sun-hotspot-igv-view-actions-LineGeneratorAction.shadow/com-sun-hotspot-igv-coordinator-actions-OpenGraphAction.shadow" boolvalue="true"/>
+
+    <folder name="QuickSearch">
+        <folder name="Nodes">
+            <attr name="command" stringvalue="n"/>
+            <attr name="position" intvalue="0"/>
+            <file name="com-sun-hotspot-igv-view-NodeQuickSearch.instance"/>
+        </folder>
+    </folder>
+    
+    <folder name="QuickSearchShadow">
+        <file name="org-netbeans-modules-quicksearch-QuickSearchAction.shadow">
+            <attr name="originalFile" stringvalue="Actions/Edit/org-netbeans-modules-quicksearch-QuickSearchAction.instance"/>
+            
+        </file>    
+    </folder>
+    <folder name="Windows2">
+        <folder name="Modes">
+            <folder name="properties">
+                <file name="properties.wstcref" url="propertiesWstcref.xml"/>
+            </folder>
+            <file name="properties.wsmode" url="propertiesWsmode.xml"/>
         </folder>
     </folder>
 </filesystem>
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/propertiesWsmode.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,18 @@
+<?xml version="1.0" encoding="UTF-8"?>
+
+<!DOCTYPE mode PUBLIC
+          "-//NetBeans//DTD Mode Properties 2.0//EN"
+          "http://www.netbeans.org/dtds/mode-properties2_0.dtd">
+
+<mode version="2.0">
+    <name unique="properties" />
+    <kind type="view" />
+    <state type="joined" />
+    <constraints>
+        <path orientation="horizontal" number="90" weight="0.2"/>
+        <path orientation="vertical" number="1" weight="0.50"/>
+    </constraints>
+    <relative-bounds x="75" y="56" width="15" height="32" />
+    <active-tc id="properties" />
+    <empty-behavior permanent="true" />
+</mode>
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/propertiesWstcref.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,11 @@
+<?xml version="1.0" encoding="UTF-8"?>
+
+<!DOCTYPE tc-ref PUBLIC
+          "-//NetBeans//DTD Top Component in Mode Properties 2.0//EN"
+          "http://www.netbeans.org/dtds/tc-ref2_0.dtd">
+
+<tc-ref version="2.0">
+    <module name="org.netbeans.core.ui/1" spec="1.2" />
+    <tc-id id="properties" />
+    <state opened="true" />
+</tc-ref>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/widgets/BlockWidget.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/widgets/BlockWidget.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -74,7 +74,7 @@
         g.setColor(titleColor);
         g.setFont(titleFont);
 
-        String s = "B" + blockNode.toString();
+        String s = "B" + blockNode.getName();
         Rectangle2D r1 = g.getFontMetrics().getStringBounds(s, g);
         g.drawString(s, r.x + 5, r.y + (int) r1.getHeight());
         g.setStroke(old);
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/widgets/DiagramConnectionWidget.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,251 +0,0 @@
-/*
- * Copyright (c) 2008, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- *
- */
-package com.sun.hotspot.igv.view.widgets;
-
-import com.sun.hotspot.igv.graph.Connection;
-import com.sun.hotspot.igv.graph.Figure;
-import com.sun.hotspot.igv.view.DiagramScene;
-import java.awt.BasicStroke;
-import java.awt.Color;
-import java.awt.Composite;
-import java.awt.Graphics2D;
-import java.awt.Point;
-import java.awt.Rectangle;
-import java.awt.Stroke;
-import java.util.ArrayList;
-import java.util.List;
-import org.netbeans.api.visual.anchor.AnchorShape;
-import org.netbeans.api.visual.model.ObjectState;
-import org.netbeans.api.visual.widget.ConnectionWidget;
-import org.netbeans.api.visual.widget.Scene;
-
-/**
- *
- * @author Thomas Wuerthinger
- */
-public class DiagramConnectionWidget extends ConnectionWidget {
-
-    private static Stroke DASHED_STROKE = new BasicStroke(
-            1,
-            BasicStroke.CAP_BUTT,
-            BasicStroke.JOIN_ROUND,
-            0,
-            new float[]{2},
-            0);
-    private static Stroke NORMAL_STROKE = new BasicStroke(1);
-    private static Stroke BOLD_STROKE = new BasicStroke(3);
-    public static int WHITE_FACTOR = 5;
-    private Connection connection;
-    private Color color;
-    private Point lastSourceAnchor;
-    private Point lastTargetAnchor;
-    private List<Point> controlPoints;
-    private Rectangle clientArea;
-    private boolean split;
-    private int[] xPoints;
-    private int[] yPoints;
-    private int pointCount;
-
-    /** Creates a new instance of ConnectionWidget */
-    public DiagramConnectionWidget(Connection connection, Scene scene) {
-        super(scene);
-        this.connection = connection;
-        color = connection.getColor();
-        if (connection.getStyle() == Connection.ConnectionStyle.DASHED) {
-            this.setStroke(DASHED_STROKE);
-        } else if (connection.getStyle() == Connection.ConnectionStyle.BOLD) {
-            this.setStroke(BOLD_STROKE);
-        } else {
-            this.setStroke(NORMAL_STROKE);
-        }
-        this.setCheckClipping(true);
-        clientArea = new Rectangle();
-        updateControlPoints();
-    }
-
-    public Connection getConnection() {
-        return connection;
-    }
-
-    public void updateControlPoints() {
-        List<Point> newControlPoints = connection.getControlPoints();
-        Connection c = connection;
-        Figure f = c.getInputSlot().getFigure();
-        Point p = new Point(f.getPosition());
-        p.translate(c.getInputSlot().getRelativePosition().x, f.getSize().height / 2);
-        Point p4 = new Point(f.getPosition());
-        p4.translate(c.getInputSlot().getRelativePosition().x, c.getInputSlot().getRelativePosition().y);
-
-        Figure f2 = c.getOutputSlot().getFigure();
-        Point p2 = new Point(f2.getPosition());
-        p2.translate(c.getOutputSlot().getRelativePosition().x, f2.getSize().height / 2);
-        Point p3 = new Point(f2.getPosition());
-        p3.translate(c.getOutputSlot().getRelativePosition().x, c.getOutputSlot().getRelativePosition().y);
-
-        /*if(controlPoints.size() >= 2) {
-        String className = Preferences.userNodeForPackage(PreferenceConstants.class).get(PreferenceConstants.KEY_LINE_GENERATOR, PreferenceConstants.DEFAULT_LINE_GENERATOR);
-        try {
-        LineGenerator lg = (LineGenerator)Class.forName(className).newInstance();
-        controlPoints = lg.createLine(controlPoints, p2, p);
-        } catch (InstantiationException ex) {
-        } catch (IllegalAccessException ex) {
-        } catch (ClassNotFoundException ex) {
-        }
-        }*/
-
-        this.controlPoints = newControlPoints;
-        pointCount = newControlPoints.size();
-        xPoints = new int[pointCount];
-        yPoints = new int[pointCount];
-        int minX = Integer.MAX_VALUE;
-        int maxX = Integer.MIN_VALUE;
-        int minY = Integer.MAX_VALUE;
-        int maxY = Integer.MIN_VALUE;
-        split = false;
-        for (int i = 0; i < pointCount; i++) {
-            if (newControlPoints.get(i) == null) {
-                split = true;
-            } else {
-                int curX = newControlPoints.get(i).x;
-                int curY = newControlPoints.get(i).y;
-                this.xPoints[i] = curX;
-                this.yPoints[i] = curY;
-                minX = Math.min(minX, curX);
-                maxX = Math.max(maxX, curX);
-                minY = Math.min(minY, curY);
-                maxY = Math.max(maxY, curY);
-            }
-        }
-
-        this.clientArea = new Rectangle(minX, minY, maxX - minX, maxY - minY);
-    }
-
-    @Override
-    protected void paintWidget() {
-        Graphics2D g = this.getGraphics();
-
-        if (xPoints.length == 0 || Math.abs(xPoints[0] - xPoints[xPoints.length - 1]) > 2000) {
-            return;
-        }
-
-        //g.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_OFF);
-        //g.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_SPEED);
-        //g.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_OFF);
-
-        DiagramScene ds = (DiagramScene) this.getScene();
-        boolean shouldHide = false;//ds.getShouldHide(this);
-
-        Composite oldComposite = null;
-        if (shouldHide) {
-            Color c = new Color(255 - (255 - color.getRed()) / WHITE_FACTOR, 255 - (255 - color.getGreen()) / WHITE_FACTOR, 255 - (255 - color.getBlue()) / WHITE_FACTOR);
-            g.setPaint(c);
-        } else {
-            g.setPaint(color);
-        }
-
-        if (split) {
-            for (int i = 1; i < controlPoints.size(); i++) {
-                Point prev = controlPoints.get(i - 1);
-                Point cur = controlPoints.get(i);
-                if (cur == null || prev == null) {
-                    continue;
-                }
-
-                g.drawLine(prev.x, prev.y, cur.x, cur.y);
-            }
-        } else {
-            g.drawPolyline(xPoints, yPoints, pointCount);
-        }
-
-        /*for(int i=0; i<xPoints.length; i++) {
-        int x = xPoints[i];
-        int y = yPoints[i];
-        g.fillOval(x - 2, y - 2, 4, 4);
-        }*/
-
-        if (xPoints.length >= 2) {
-            Graphics2D g2 = (Graphics2D) g.create();
-            int xOff = xPoints[xPoints.length - 2] - xPoints[xPoints.length - 1];
-            int yOff = yPoints[yPoints.length - 2] - yPoints[yPoints.length - 1];
-            if (xOff == 0 && yOff == 0 && yPoints.length >= 3) {
-                xOff = xPoints[xPoints.length - 3] - xPoints[xPoints.length - 1];
-                yOff = yPoints[yPoints.length - 3] - yPoints[yPoints.length - 1];
-            }
-            g2.translate(xPoints[xPoints.length - 1], yPoints[yPoints.length - 1]);
-            g2.rotate(Math.atan2(yOff, xOff));
-
-            g2.scale(0.55, 0.80);
-            AnchorShape.TRIANGLE_FILLED.paint(g2, false);
-        }
-    }
-
-    @Override
-    public void notifyStateChanged(ObjectState previousState, ObjectState state) {
-
-        if (previousState.isHovered() != state.isHovered()) {
-            color = connection.getColor();
-            if (state.isHovered()) {
-                this.setStroke(BOLD_STROKE);
-            } else {
-                this.setStroke(NORMAL_STROKE);
-            }
-
-            if (state.isHovered()) {
-                this.setStroke(BOLD_STROKE);
-            } else {
-                this.setStroke(NORMAL_STROKE);
-            }
-
-            repaint();
-        }
-        super.notifyStateChanged(previousState, state);
-    }
-
-    @Override
-    public List<Point> getControlPoints() {
-        if (split) {
-            ArrayList<Point> result = new ArrayList<Point>();
-            for (Point p : controlPoints) {
-                if (p != null) {
-                    result.add(p);
-                }
-            }
-            return result;
-        } else {
-            return controlPoints;
-        }
-    }
-
-    @Override
-    public String toString() {
-        return "ConnectionWidget[" + connection + "]";
-    }
-
-    @Override
-    protected Rectangle calculateClientArea() {
-        Rectangle result = new Rectangle(clientArea);
-        result.grow(10, 10);
-        return result;
-    }
-}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/widgets/FigureWidget.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/widgets/FigureWidget.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,36 +23,37 @@
  */
 package com.sun.hotspot.igv.view.widgets;
 
+import com.sun.hotspot.igv.data.InputGraph;
+import com.sun.hotspot.igv.data.Properties;
+import com.sun.hotspot.igv.data.services.GraphViewer;
 import com.sun.hotspot.igv.graph.Figure;
-import com.sun.hotspot.igv.view.DiagramScene;
-import com.sun.hotspot.igv.view.SlotLayout;
+import com.sun.hotspot.igv.util.DoubleClickAction;
 import com.sun.hotspot.igv.util.DoubleClickHandler;
-import com.sun.hotspot.igv.data.Properties;
 import com.sun.hotspot.igv.util.PropertiesSheet;
-import java.awt.AlphaComposite;
-import java.awt.Color;
-import java.awt.Composite;
-import java.awt.Dimension;
-import java.awt.Font;
-import java.awt.Graphics;
-import java.awt.Point;
+import com.sun.hotspot.igv.view.DiagramScene;
+import java.awt.*;
+import java.awt.event.ActionEvent;
 import java.util.ArrayList;
 import java.util.HashSet;
 import java.util.Set;
+import javax.swing.AbstractAction;
 import javax.swing.Action;
 import javax.swing.BorderFactory;
 import javax.swing.JMenu;
 import javax.swing.JPopupMenu;
+import javax.swing.event.MenuEvent;
+import javax.swing.event.MenuListener;
 import org.netbeans.api.visual.action.PopupMenuProvider;
 import org.netbeans.api.visual.action.WidgetAction;
+import org.netbeans.api.visual.layout.LayoutFactory;
 import org.netbeans.api.visual.model.ObjectState;
+import org.netbeans.api.visual.widget.LabelWidget;
 import org.netbeans.api.visual.widget.Widget;
-import org.netbeans.api.visual.layout.LayoutFactory;
-import org.netbeans.api.visual.widget.LabelWidget;
 import org.openide.nodes.AbstractNode;
 import org.openide.nodes.Children;
 import org.openide.nodes.Node;
 import org.openide.nodes.Sheet;
+import org.openide.util.Lookup;
 
 /**
  *
@@ -61,12 +62,7 @@
 public class FigureWidget extends Widget implements Properties.Provider, PopupMenuProvider, DoubleClickHandler {
 
     public static final boolean VERTICAL_LAYOUT = true;
-    public static final int DEPTH = 5;
-    public static final int MAX_STRING_LENGTH = 20;
     private static final double LABEL_ZOOM_FACTOR = 0.3;
-    private static final double ZOOM_FACTOR = 0.1;
-    private Font font;
-    private Font boldFont;
     private Figure figure;
     private Widget leftWidget;
     private Widget rightWidget;
@@ -74,7 +70,8 @@
     private ArrayList<LabelWidget> labelWidgets;
     private DiagramScene diagramScene;
     private boolean boundary;
-    private Node node;
+    private final Node node;
+    private Widget dummyTop;
 
     public void setBoundary(boolean b) {
         boundary = b;
@@ -88,80 +85,58 @@
         return node;
     }
 
-    private String shortenString(String string) {
-        if (string.length() > MAX_STRING_LENGTH) {
-            StringBuilder sb = new StringBuilder();
-            for (int i = 0; i < string.length(); i++) {
-                char c = string.charAt(i);
-                if (!Character.isLetter(c) || Character.isUpperCase(c)) {
-                    sb.append(c);
-                }
-            }
-            string = sb.toString();
-        }
-        return string;
+    @Override
+    public boolean isHitAt(Point localLocation) {
+        return middleWidget.isHitAt(localLocation);
     }
 
-    public FigureWidget(final Figure f, DiagramScene s, Widget parent) {
-
-        super(s);
-
+    public FigureWidget(final Figure f, WidgetAction hoverAction, WidgetAction selectAction, DiagramScene scene, Widget parent) {
+        super(scene);
 
-        font = f.getDiagram().getFont();
-        boldFont = f.getDiagram().getFont().deriveFont(Font.BOLD);
-        this.setCheckClipping(true);
-        this.diagramScene = s;
-
-        parent.addChild(this);
-        this.figure = f;
-        this.resolveBounds(null, calculateClientArea());
+        assert this.getScene() != null;
+        assert this.getScene().getView() != null;
 
-        leftWidget = new Widget(s);
-        this.addChild(leftWidget);
-        leftWidget.setLayout(new SlotLayout(SlotLayout.HorizontalAlignment.Right, VERTICAL_LAYOUT));//LayoutFactory.createVerticalFlowLayout(LayoutFactory.SerialAlignment.JUSTIFY, 0));
-
-        middleWidget = new Widget(s);
-        this.addChild(middleWidget);
+        this.figure = f;
+        this.setCheckClipping(true);
+        this.diagramScene = scene;
+        parent.addChild(this);
 
-        if (VERTICAL_LAYOUT) {
-            this.setLayout(LayoutFactory.createVerticalFlowLayout());
-        } else {
-            this.setLayout(LayoutFactory.createHorizontalFlowLayout());
-        }
+        Widget outer = new Widget(scene);
+        outer.setBackground(f.getColor());
+        outer.setLayout(LayoutFactory.createOverlayLayout());
 
-        middleWidget.setLayout(LayoutFactory.createVerticalFlowLayout());
-
+        middleWidget = new Widget(scene);
+        middleWidget.setLayout(LayoutFactory.createVerticalFlowLayout(LayoutFactory.SerialAlignment.CENTER, 0));
         middleWidget.setBackground(f.getColor());
         middleWidget.setOpaque(true);
-        assert this.getScene() != null;
-        assert this.getScene().getView() != null;
-        middleWidget.setBorder(BorderFactory.createLineBorder(Color.BLACK));
+        middleWidget.getActions().addAction(new DoubleClickAction(this));
+        middleWidget.setCheckClipping(true);
 
-
-        labelWidgets = new ArrayList<LabelWidget>();
+        dummyTop = new Widget(scene);
+        dummyTop.setMinimumSize(new Dimension(Figure.INSET / 2, 1));
+        middleWidget.addChild(dummyTop);
 
         String[] strings = figure.getLines();
-
-        for (String cur : strings) {
+        labelWidgets = new ArrayList<>(strings.length);
 
-            String displayString = cur;
-
-            LabelWidget lw = new LabelWidget(s);
+        for (String displayString : strings) {
+            LabelWidget lw = new LabelWidget(scene);
             labelWidgets.add(lw);
             middleWidget.addChild(lw);
             lw.setLabel(displayString);
-
-            lw.setFont(font);
-            lw.setForeground(Color.BLACK);
+            lw.setFont(figure.getDiagram().getFont());
+            lw.setForeground(getTextColor());
             lw.setAlignment(LabelWidget.Alignment.CENTER);
             lw.setVerticalAlignment(LabelWidget.VerticalAlignment.CENTER);
-            lw.setMaximumSize(new Dimension(f.getWidth(), 20000));
-            lw.setMinimumSize(new Dimension(f.getWidth(), 20));
+            lw.setBorder(BorderFactory.createEmptyBorder());
         }
 
-        rightWidget = new Widget(s);
-        this.addChild(rightWidget);
-        rightWidget.setLayout(new SlotLayout(SlotLayout.HorizontalAlignment.Left, VERTICAL_LAYOUT));//LayoutFactory.createVerticalLayout(LayoutFactory.SerialAlignment.JUSTIFY, 0));
+        Widget dummyBottom = new Widget(scene);
+        dummyBottom.setMinimumSize(new Dimension(Figure.INSET / 2, 1));
+        middleWidget.addChild(dummyBottom);
+
+        middleWidget.setPreferredBounds(new Rectangle(0, Figure.SLOT_WIDTH - Figure.OVERLAPPING, f.getWidth(), f.getHeight()));
+        this.addChild(middleWidget);
 
         // Initialize node for property sheet
         node = new AbstractNode(Children.LEAF) {
@@ -175,22 +150,6 @@
         };
         node.setDisplayName(getName());
     }
-    private boolean firstTime = true;
-
-    @Override
-    protected void paintWidget() {
-        if (firstTime) {
-            firstTime = false;
-            for (LabelWidget w : labelWidgets) {
-                String cur = w.getLabel();
-                Graphics graphics = this.getGraphics();
-                if (graphics.getFontMetrics().stringWidth(cur) > figure.getWidth()) {
-                    w.setLabel(shortenString(cur));
-                }
-            }
-        }
-        super.paintWidget();
-    }
 
     public Widget getLeftWidget() {
         return leftWidget;
@@ -204,40 +163,29 @@
     protected void notifyStateChanged(ObjectState previousState, ObjectState state) {
         super.notifyStateChanged(previousState, state);
 
-        Color borderColor = Color.BLACK;
-        int thickness = 1;
-        boolean repaint = false;
-        Font f = font;
+        Font font = this.figure.getDiagram().getFont();
         if (state.isSelected()) {
-            thickness = 1;
-            f = boldFont;
-        }
-
-        if (state.isHovered()) {
-            borderColor = Color.BLUE;
+            font = this.figure.getDiagram().getBoldFont();
         }
 
-        if (state.isHovered() != previousState.isHovered()) {
-            repaint = true;
-        }
-
-        if (state.isSelected() != previousState.isSelected()) {
-            repaint = true;
+        Color borderColor = Color.BLACK;
+        Color innerBorderColor = getFigure().getColor();
+        if (state.isHighlighted()) {
+            innerBorderColor = borderColor = Color.BLUE;
         }
 
-        if (repaint) {
-            middleWidget.setBorder(BorderFactory.createLineBorder(borderColor, thickness));
-            for (LabelWidget labelWidget : labelWidgets) {
-                labelWidget.setFont(f);
-            }
-            repaint();
+        middleWidget.setBorder(BorderFactory.createCompoundBorder(BorderFactory.createLineBorder(borderColor, 1), BorderFactory.createLineBorder(innerBorderColor, 1)));
+        for (LabelWidget labelWidget : labelWidgets) {
+            labelWidget.setFont(font);
         }
+        repaint();
     }
 
     public String getName() {
         return getProperties().get("name");
     }
 
+    @Override
     public Properties getProperties() {
         return figure.getProperties();
     }
@@ -246,13 +194,18 @@
         return figure;
     }
 
+    private Color getTextColor() {
+        Color bg = figure.getColor();
+        double brightness = bg.getRed() * 0.21 + bg.getGreen() * 0.72 + bg.getBlue() * 0.07;
+        if (brightness < 150) {
+            return Color.WHITE;
+        } else {
+            return Color.BLACK;
+        }
+    }
+
     @Override
     protected void paintChildren() {
-
-        if (diagramScene.getRealZoomFactor() < ZOOM_FACTOR && diagramScene.getModel().getShowBlocks()) {
-            return;
-        }
-
         Composite oldComposite = null;
         if (boundary) {
             oldComposite = getScene().getGraphics().getComposite();
@@ -260,8 +213,7 @@
             this.getScene().getGraphics().setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER, alpha));
         }
 
-        if (diagramScene.getRealZoomFactor() < LABEL_ZOOM_FACTOR) {
-
+        if (diagramScene.getZoomFactor() < LABEL_ZOOM_FACTOR) {
             for (LabelWidget labelWidget : labelWidgets) {
                 labelWidget.setVisible(false);
             }
@@ -269,9 +221,20 @@
             for (LabelWidget labelWidget : labelWidgets) {
                 labelWidget.setVisible(true);
             }
-
         } else {
+            Color oldColor = null;
+            if (boundary) {
+                for (LabelWidget labelWidget : labelWidgets) {
+                    oldColor = labelWidget.getForeground();
+                    labelWidget.setForeground(Color.BLACK);
+                }
+            }
             super.paintChildren();
+            if (boundary) {
+                for (LabelWidget labelWidget : labelWidgets) {
+                    labelWidget.setForeground(oldColor);
+                }
+            }
         }
 
         if (boundary) {
@@ -279,80 +242,126 @@
         }
     }
 
+    @Override
     public JPopupMenu getPopupMenu(Widget widget, Point point) {
-        JPopupMenu m = diagramScene.createPopupMenu();
+        JPopupMenu menu = diagramScene.createPopupMenu();
+        menu.addSeparator();
 
-        JMenu predecessors = new JMenu("Predecessors");
-        addFigureToSubMenu(predecessors, getFigure(), false, DEPTH);
+        build(menu, getFigure(), this, false, diagramScene);
+        menu.addSeparator();
+        build(menu, getFigure(), this, true, diagramScene);
+
+        if (getFigure().getSubgraphs() != null) {
+            menu.addSeparator();
+            JMenu subgraphs = new JMenu("Subgraphs");
+            menu.add(subgraphs);
 
-        JMenu successors = new JMenu("Successors");
-        addFigureToSubMenu(successors, getFigure(), true, DEPTH);
+            final GraphViewer viewer = Lookup.getDefault().lookup(GraphViewer.class);
+            for (final InputGraph subgraph : getFigure().getSubgraphs()) {
+                Action a = new AbstractAction() {
 
-        m.addSeparator();
-        m.add(predecessors);
-        m.add(successors);
-        return m;
+                    @Override
+                    public void actionPerformed(ActionEvent e) {
+                        viewer.view(subgraph, true);
+                    }
+                };
+
+                a.setEnabled(true);
+                a.putValue(Action.NAME, subgraph.getName());
+                subgraphs.add(a);
+            }
+        }
+
+        return menu;
     }
 
-    public void addFigureToSubMenu(JMenu subMenu, final Figure f, boolean successor, int depth) {
-        Set<Figure> set = f.getPredecessorSet();
-        if (successor) {
-            set = f.getSuccessorSet();
+    public static void build(JPopupMenu menu, Figure figure, FigureWidget figureWidget, boolean successors, DiagramScene diagramScene) {
+        Set<Figure> set = figure.getPredecessorSet();
+        if (successors) {
+            set = figure.getSuccessorSet();
         }
 
-        int count = set.size();
-        if (set.contains(f)) {
-            count--;
-        }
-
-        for (Figure f2 : set) {
-            if (f2 == f) {
+        boolean first = true;
+        for (Figure f : set) {
+            if (f == figure) {
                 continue;
             }
 
-            count--;
-            addFigureToMenu(subMenu, f2, successor, depth - 1);
-            if (count > 0) {
-                subMenu.addSeparator();
+            if (first) {
+                first = false;
+            } else {
+                menu.addSeparator();
             }
+
+            Action go = diagramScene.createGotoAction(f);
+            menu.add(go);
+
+            JMenu preds = new JMenu("Nodes Above");
+            preds.addMenuListener(figureWidget.new NeighborMenuListener(preds, f, false));
+            menu.add(preds);
+
+            JMenu succs = new JMenu("Nodes Below");
+            succs.addMenuListener(figureWidget.new NeighborMenuListener(succs, f, true));
+            menu.add(succs);
+        }
+
+        if (figure.getPredecessorSet().isEmpty() && figure.getSuccessorSet().isEmpty()) {
+            menu.add("(none)");
         }
     }
 
-    public void addFigureToMenu(JMenu m, final Figure f, boolean successor, int depth) {
+    /**
+     * Builds the submenu for a figure's neighbors on demand.
+     */
+    public class NeighborMenuListener implements MenuListener {
 
-        Action a = diagramScene.createGotoAction(f);
-
+        private final JMenu menu;
+        private final Figure figure;
+        private final boolean successors;
 
-        m.add(a);
+        public NeighborMenuListener(JMenu menu, Figure figure, boolean successors) {
+            this.menu = menu;
+            this.figure = figure;
+            this.successors = successors;
+        }
 
-        if (depth > 0) {
-            String name = "Predecessors";
-            if (successor) {
-                name = "Successors";
+        @Override
+        public void menuSelected(MenuEvent e) {
+            if (menu.getItemCount() > 0) {
+                // already built before
+                return;
             }
 
-            JMenu subMenu = new JMenu(name);
-            addFigureToSubMenu(subMenu, f, successor, depth);
-            m.add(subMenu);
+            build(menu.getPopupMenu(), figure, FigureWidget.this, successors, diagramScene);
+        }
+
+        @Override
+        public void menuDeselected(MenuEvent e) {
+            // ignore
         }
 
+        @Override
+        public void menuCanceled(MenuEvent e) {
+            // ignore
+        }
     }
 
+    @Override
     public void handleDoubleClick(Widget w, WidgetAction.WidgetMouseEvent e) {
 
         if (diagramScene.isAllVisible()) {
-            Set<Integer> hiddenNodes = new HashSet<Integer>(diagramScene.getModel().getGraphToView().getGroup().getAllNodes());
+            final Set<Integer> hiddenNodes = new HashSet<>(diagramScene.getModel().getGraphToView().getGroup().getAllNodes());
             hiddenNodes.removeAll(this.getFigure().getSource().getSourceNodesAsSet());
-            this.diagramScene.showNot(hiddenNodes);
+            this.diagramScene.getModel().showNot(hiddenNodes);
         } else if (isBoundary()) {
 
-            Set<Integer> hiddenNodes = new HashSet<Integer>(diagramScene.getModel().getHiddenNodes());
+            final Set<Integer> hiddenNodes = new HashSet<>(diagramScene.getModel().getHiddenNodes());
             hiddenNodes.removeAll(this.getFigure().getSource().getSourceNodesAsSet());
-            this.diagramScene.showNot(hiddenNodes);
+            this.diagramScene.getModel().showNot(hiddenNodes);
         } else {
-            Set<Integer> hiddenNodes = new HashSet<Integer>(diagramScene.getModel().getHiddenNodes());
+            final Set<Integer> hiddenNodes = new HashSet<>(diagramScene.getModel().getHiddenNodes());
             hiddenNodes.addAll(this.getFigure().getSource().getSourceNodesAsSet());
-            this.diagramScene.showNot(hiddenNodes);
+            this.diagramScene.getModel().showNot(hiddenNodes);
         }
     }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/widgets/InputSlotWidget.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/widgets/InputSlotWidget.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,6 +23,7 @@
  */
 package com.sun.hotspot.igv.view.widgets;
 
+import com.sun.hotspot.igv.graph.Figure;
 import com.sun.hotspot.igv.graph.InputSlot;
 import com.sun.hotspot.igv.view.DiagramScene;
 import java.awt.Point;
@@ -40,14 +41,25 @@
     public InputSlotWidget(InputSlot slot, DiagramScene scene, Widget parent, FigureWidget fw) {
         super(slot, scene, parent, fw);
         inputSlot = slot;
-        init();
-        getFigureWidget().getLeftWidget().addChild(this);
+        //init();
+        //getFigureWidget().getLeftWidget().addChild(this);
+        Point p = inputSlot.getRelativePosition();
+        p.x -= this.calculateClientArea().width / 2;
+        p.y += Figure.SLOT_START;
+        this.setPreferredLocation(p);
     }
 
     public InputSlot getInputSlot() {
         return inputSlot;
     }
 
+    @Override
+    protected int calculateSlotWidth() {
+        List<InputSlot> slots = getSlot().getFigure().getInputSlots();
+        assert slots.contains(getSlot());
+        return calculateWidth(slots.size());
+    }
+/*
     protected Point calculateRelativeLocation() {
         if (getFigureWidget().getBounds() == null) {
             return new Point(0, 0);
@@ -57,5 +69,5 @@
         List<InputSlot> slots = inputSlot.getFigure().getInputSlots();
         assert slots.contains(inputSlot);
         return new Point((int) x, (int) (calculateRelativeY(slots.size(), slots.indexOf(inputSlot))));
-    }
+    }*/
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/widgets/LineWidget.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/widgets/LineWidget.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -24,23 +24,22 @@
 package com.sun.hotspot.igv.view.widgets;
 
 import com.sun.hotspot.igv.graph.Connection;
+import com.sun.hotspot.igv.graph.Figure;
 import com.sun.hotspot.igv.graph.InputSlot;
 import com.sun.hotspot.igv.graph.OutputSlot;
 import com.sun.hotspot.igv.view.DiagramScene;
-import java.awt.BasicStroke;
-import java.awt.Color;
-import java.awt.Graphics2D;
-import java.awt.Point;
-import java.awt.Rectangle;
-import java.awt.Stroke;
+import java.awt.*;
 import java.awt.geom.Line2D;
 import java.util.ArrayList;
+import java.util.HashSet;
 import java.util.List;
+import java.util.Set;
 import javax.swing.JPopupMenu;
 import javax.swing.event.PopupMenuEvent;
 import javax.swing.event.PopupMenuListener;
 import org.netbeans.api.visual.action.ActionFactory;
 import org.netbeans.api.visual.action.PopupMenuProvider;
+import org.netbeans.api.visual.action.SelectProvider;
 import org.netbeans.api.visual.animator.SceneAnimator;
 import org.netbeans.api.visual.model.ObjectState;
 import org.netbeans.api.visual.widget.Widget;
@@ -51,7 +50,7 @@
  */
 public class LineWidget extends Widget implements PopupMenuProvider {
 
-    public final int BORDER = 8;
+    public final int BORDER = 5;
     public final int ARROW_SIZE = 6;
     public final int BOLD_ARROW_SIZE = 7;
     public final int HOVER_ARROW_SIZE = 8;
@@ -80,7 +79,7 @@
         this.from = from;
         this.to = to;
         this.predecessor = predecessor;
-        this.successors = new ArrayList<LineWidget>();
+        this.successors = new ArrayList<>();
         if (predecessor != null) {
             predecessor.addSuccessor(this);
         }
@@ -110,6 +109,7 @@
         if (connections.size() > 0) {
             color = connections.get(0).getColor();
         }
+        this.setToolTipText("<HTML>" + generateToolTipText(this.connections) + "</HTML>");
 
         this.setCheckClipping(true);
 
@@ -120,6 +120,38 @@
             this.setBackground(Color.WHITE);
             animator.animateBackgroundColor(this, color);
         }
+
+        this.getActions().addAction(ActionFactory.createSelectAction(new SelectProvider() {
+
+            @Override
+            public boolean isAimingAllowed(Widget arg0, Point arg1, boolean arg2) {
+                return true;
+            }
+
+            @Override
+            public boolean isSelectionAllowed(Widget arg0, Point arg1, boolean arg2) {
+                return true;
+            }
+
+            @Override
+            public void select(Widget arg0, Point arg1, boolean arg2) {
+                Set<Figure> set = new HashSet<>();
+                for (Connection c : LineWidget.this.connections) {
+                    set.add(c.getInputSlot().getFigure());
+                    set.add(c.getOutputSlot().getFigure());
+                }
+                LineWidget.this.scene.setSelectedObjects(set);
+            }
+        }));
+    }
+
+    private String generateToolTipText(List<Connection> conn) {
+        StringBuilder sb = new StringBuilder();
+        for (Connection c : conn) {
+            sb.append(c.getToolTipText());
+            sb.append("<br>");
+        }
+        return sb.toString();
     }
 
     public Point getFrom() {
@@ -141,13 +173,12 @@
 
     @Override
     protected void paintWidget() {
-        if (scene.getRealZoomFactor() < ZOOM_FACTOR) {
+        if (scene.getZoomFactor() < ZOOM_FACTOR) {
             return;
         }
 
         Graphics2D g = getScene().getGraphics();
         g.setPaint(this.getBackground());
-        ObjectState state = this.getState();
         float width = 1.0f;
 
         if (isBold) {
@@ -171,7 +202,7 @@
         g.drawLine(from.x, from.y, to.x, to.y);
 
         boolean sameFrom = false;
-        boolean sameTo = successors.size() == 0;
+        boolean sameTo = successors.isEmpty();
         for (LineWidget w : successors) {
             if (w.getFrom().equals(getTo())) {
                 sameTo = true;
@@ -207,6 +238,20 @@
 
     private void setHighlighted(boolean b) {
         this.highlighted = b;
+        Set<Object> highlightedObjects = new HashSet<>(scene.getHighlightedObjects());
+        Set<Object> highlightedObjectsChange = new HashSet<>();
+        for (Connection c : connections) {
+            highlightedObjectsChange.add(c.getInputSlot().getFigure());
+            highlightedObjectsChange.add(c.getInputSlot());
+            highlightedObjectsChange.add(c.getOutputSlot().getFigure());
+            highlightedObjectsChange.add(c.getOutputSlot());
+        }
+        if(b) {
+            highlightedObjects.addAll(highlightedObjectsChange);
+        } else {
+            highlightedObjects.removeAll(highlightedObjectsChange);
+        }
+        scene.setHighlightedObjects(highlightedObjects);
         this.revalidate(true);
     }
 
@@ -263,6 +308,7 @@
         }
     }
 
+    @Override
     public JPopupMenu getPopupMenu(Widget widget, Point localLocation) {
         JPopupMenu menu = new JPopupMenu();
         menu.add(scene.createGotoAction(outputSlot.getFigure()));
@@ -276,14 +322,17 @@
         final LineWidget w = this;
         menu.addPopupMenuListener(new PopupMenuListener() {
 
+            @Override
             public void popupMenuWillBecomeVisible(PopupMenuEvent e) {
                 w.setRecursivePopupVisible(true);
             }
 
+            @Override
             public void popupMenuWillBecomeInvisible(PopupMenuEvent e) {
                 w.setRecursivePopupVisible(false);
             }
 
+            @Override
             public void popupMenuCanceled(PopupMenuEvent e) {
             }
         });
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/widgets/MultiConnectionWidget.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,281 +0,0 @@
-/*
- * Copyright (c) 2008, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- *
- */
-package com.sun.hotspot.igv.view.widgets;
-
-import com.sun.hotspot.igv.graph.Connection;
-import com.sun.hotspot.igv.graph.InputSlot;
-import com.sun.hotspot.igv.graph.OutputSlot;
-import com.sun.hotspot.igv.graph.Slot;
-import com.sun.hotspot.igv.view.DiagramScene;
-import java.awt.BasicStroke;
-import java.awt.Color;
-import java.awt.Graphics2D;
-import java.awt.Point;
-import java.awt.Rectangle;
-import java.awt.Stroke;
-import java.awt.geom.Line2D;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-import java.util.SortedSet;
-import java.util.TreeSet;
-import javax.swing.JPopupMenu;
-import javax.swing.event.PopupMenuEvent;
-import javax.swing.event.PopupMenuListener;
-import org.netbeans.api.visual.action.PopupMenuProvider;
-import org.netbeans.api.visual.model.ObjectState;
-import org.netbeans.api.visual.widget.Widget;
-
-/**
- *
- * @author Thomas Wuerthinger
- */
-public class MultiConnectionWidget extends Widget implements PopupMenuProvider {
-
-    public final int BORDER = 4;
-    public final int HOVER_STROKE_WIDTH = 3;
-
-    private static class Route {
-
-        public Point from;
-        public Point to;
-        public SortedSet<InputSlot> inputSlots;
-        public boolean decorateStart;
-        public boolean decorateEnd;
-
-        public Route(Point from, Point to) {
-            assert from != null;
-            assert to != null;
-            this.from = from;
-            this.to = to;
-            this.inputSlots = new TreeSet<InputSlot>();
-        }
-
-        @Override
-        public boolean equals(Object obj) {
-
-            if (obj instanceof Route) {
-                Route r = (Route) obj;
-                return r.from.equals(from) && r.to.equals(to);
-            }
-
-            return super.equals(obj);
-        }
-
-        @Override
-        public int hashCode() {
-            return ((((from.x * 1711) + from.y) * 1711 + to.x) * 1711 + to.y);
-        }
-    }
-    private Rectangle clientArea;
-    private OutputSlot outputSlot;
-    private Map<Route, SortedSet<InputSlot>> routeMap;
-    private List<Route> routeList;
-    private Color color;
-    private DiagramScene diagramScene;
-    private boolean popupVisible;
-
-    /** Creates a new instance of MultiConnectionWidget */
-    public MultiConnectionWidget(OutputSlot outputSlot, DiagramScene scene) {
-        super(scene);
-
-        this.diagramScene = scene;
-        this.outputSlot = outputSlot;
-        this.setCheckClipping(true);
-
-        routeMap = new HashMap<Route, SortedSet<InputSlot>>();
-        routeList = new ArrayList<Route>();
-        color = Color.BLACK;
-
-        for (Connection c : outputSlot.getConnections()) {
-            List<Point> controlPoints = c.getControlPoints();
-            InputSlot inputSlot = (InputSlot) c.getTo();
-            color = c.getColor();
-
-            for (int i = 1; i < controlPoints.size(); i++) {
-                Point prev = controlPoints.get(i - 1);
-                Point cur = controlPoints.get(i);
-
-                if (prev != null && cur != null) {
-                    Route r = new Route(prev, cur);
-                    if (routeMap.containsKey(r)) {
-                        SortedSet<InputSlot> set = routeMap.get(r);
-                        set.add(inputSlot);
-                    } else {
-                        SortedSet<InputSlot> set = new TreeSet<InputSlot>(Slot.slotFigureComparator);
-                        set.add(inputSlot);
-                        routeMap.put(r, set);
-                        routeList.add(r);
-                    }
-                }
-            }
-        }
-
-        if (routeList.size() == 0) {
-            clientArea = new Rectangle();
-        } else {
-            for (Route r : routeList) {
-
-                int x = r.from.x;
-                int y = r.from.y;
-
-                int x2 = r.to.x;
-                int y2 = r.to.y;
-
-                if (x > x2) {
-                    int tmp = x;
-                    x = x2;
-                    x2 = tmp;
-                }
-
-                if (y > y2) {
-                    int tmp = y;
-                    y = y2;
-                    y2 = tmp;
-                }
-
-                int width = x2 - x + 1;
-                int height = y2 - y + 1;
-
-                Rectangle rect = new Rectangle(x, y, width, height);
-                if (clientArea == null) {
-                    clientArea = rect;
-                } else {
-                    clientArea = clientArea.union(rect);
-                }
-            }
-
-            clientArea.grow(BORDER, BORDER);
-        }
-    }
-
-    private void setHoverPosition(Point location) {
-        Route r = getNearest(location);
-    }
-
-    private Route getNearest(Point localLocation) {
-
-        double minDist = Double.MAX_VALUE;
-        Route result = null;
-        for (Route r : routeList) {
-            double dist = Line2D.ptSegDistSq((double) r.from.x, (double) r.from.y, (double) r.to.x, (double) r.to.y, (double) localLocation.x, (double) localLocation.y);
-            if (dist < minDist) {
-                result = r;
-                minDist = dist;
-            }
-        }
-
-        assert result != null;
-
-        return result;
-    }
-
-    @Override
-    public boolean isHitAt(Point localLocation) {
-        if (!super.isHitAt(localLocation)) {
-            return false;
-        }
-
-        for (Route r : routeList) {
-            double dist = Line2D.ptSegDistSq((double) r.from.x, (double) r.from.y, (double) r.to.x, (double) r.to.y, (double) localLocation.x, (double) localLocation.y);
-            if (dist < BORDER * BORDER) {
-                setHoverPosition(localLocation);
-                return true;
-            }
-        }
-
-        return false;
-    }
-
-    @Override
-    protected Rectangle calculateClientArea() {
-        return clientArea;
-    }
-
-    @Override
-    protected void paintWidget() {
-        Graphics2D g = getScene().getGraphics();
-        //g.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_OFF);
-        g.setColor(this.color);
-        ObjectState state = this.getState();
-        float width = 1.0f;
-        if (state.isHovered() || this.popupVisible) {
-            width = HOVER_STROKE_WIDTH;
-        }
-
-        Stroke oldStroke = g.getStroke();
-        g.setStroke(new BasicStroke(width));
-        for (Route r : routeList) {
-            g.drawLine(r.from.x, r.from.y, r.to.x, r.to.y);
-        }
-        g.setStroke(oldStroke);
-    }
-
-    @Override
-    protected void notifyStateChanged(ObjectState previousState, ObjectState state) {
-
-        boolean repaint = false;
-
-        if (state.isHovered() != previousState.isHovered()) {
-            repaint = true;
-        }
-
-        repaint();
-    }
-
-    public JPopupMenu getPopupMenu(Widget widget, Point localLocation) {
-        JPopupMenu menu = new JPopupMenu();
-        Route r = getNearest(localLocation);
-        assert r != null;
-        assert routeMap.containsKey(r);
-
-        menu.add(diagramScene.createGotoAction(outputSlot.getFigure()));
-        menu.addSeparator();
-
-        SortedSet<InputSlot> set = this.routeMap.get(r);
-        for (InputSlot s : set) {
-            menu.add(diagramScene.createGotoAction(s.getFigure()));
-        }
-
-        final MultiConnectionWidget w = this;
-        menu.addPopupMenuListener(new PopupMenuListener() {
-
-            public void popupMenuWillBecomeVisible(PopupMenuEvent e) {
-                w.popupVisible = true;
-                w.repaint();
-            }
-
-            public void popupMenuWillBecomeInvisible(PopupMenuEvent e) {
-                w.popupVisible = false;
-                w.repaint();
-            }
-
-            public void popupMenuCanceled(PopupMenuEvent e) {
-            }
-        });
-
-        return menu;
-    }
-}
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/widgets/OutputSlotWidget.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/widgets/OutputSlotWidget.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -23,6 +23,7 @@
  */
 package com.sun.hotspot.igv.view.widgets;
 
+import com.sun.hotspot.igv.graph.Figure;
 import com.sun.hotspot.igv.graph.OutputSlot;
 import com.sun.hotspot.igv.view.DiagramScene;
 import java.awt.Point;
@@ -40,22 +41,21 @@
     public OutputSlotWidget(OutputSlot slot, DiagramScene scene, Widget parent, FigureWidget fw) {
         super(slot, scene, parent, fw);
         outputSlot = slot;
-        init();
-        getFigureWidget().getRightWidget().addChild(this);
+        Point p = outputSlot.getRelativePosition();
+        p.y += getSlot().getFigure().getHeight() - Figure.SLOT_START;
+        p.x -= this.calculateClientArea().width / 2;
+        this.setPreferredLocation(p);
     }
 
     public OutputSlot getOutputSlot() {
         return outputSlot;
     }
 
-    protected Point calculateRelativeLocation() {
-        if (getFigureWidget().getBounds() == null) {
-            return new Point(0, 0);
-        }
+    @Override
+    protected int calculateSlotWidth() {
+        List<OutputSlot> slots = getSlot().getFigure().getOutputSlots();
+        assert slots.contains(getSlot());
+        return calculateWidth(slots.size());
 
-        double x = this.getFigureWidget().getBounds().width;
-        List<OutputSlot> slots = outputSlot.getFigure().getOutputSlots();
-        assert slots.contains(outputSlot);
-        return new Point((int) x, (int) (calculateRelativeY(slots.size(), slots.indexOf(outputSlot))));
     }
 }
--- a/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/widgets/SlotWidget.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/View/src/com/sun/hotspot/igv/view/widgets/SlotWidget.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 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
@@ -26,51 +26,47 @@
 import com.sun.hotspot.igv.graph.Figure;
 import com.sun.hotspot.igv.graph.OutputSlot;
 import com.sun.hotspot.igv.graph.Slot;
-import com.sun.hotspot.igv.view.*;
+import com.sun.hotspot.igv.util.DoubleClickHandler;
+import com.sun.hotspot.igv.view.DiagramScene;
 import java.awt.Color;
 import java.awt.Font;
 import java.awt.Graphics2D;
-import java.awt.Image;
-import java.awt.Point;
 import java.awt.Rectangle;
 import java.awt.geom.Rectangle2D;
+import java.util.HashSet;
+import java.util.Set;
+import org.netbeans.api.visual.action.WidgetAction;
+import org.netbeans.api.visual.model.ObjectState;
 import org.netbeans.api.visual.widget.Widget;
 
 /**
  *
  * @author Thomas Wuerthinger
  */
-public abstract class SlotWidget extends Widget {
+public abstract class SlotWidget extends Widget implements DoubleClickHandler {
 
     private Slot slot;
     private FigureWidget figureWidget;
-    private Image bufferImage;
     private static double TEXT_ZOOM_FACTOR = 0.9;
     private static double ZOOM_FACTOR = 0.6;
-    private DiagramScene scene;
+    private DiagramScene diagramScene;
 
     public SlotWidget(Slot slot, DiagramScene scene, Widget parent, FigureWidget fw) {
         super(scene);
-        this.scene = scene;
+        this.diagramScene = scene;
         this.slot = slot;
         figureWidget = fw;
-        this.setToolTipText("<HTML>" + slot.getName() + "</HTML>");
+        this.setToolTipText("<HTML>" + slot.getToolTipText() + "</HTML>");
         this.setCheckClipping(true);
+        parent.addChild(this);
+
+        //this.setPreferredBounds(this.calculateClientArea());
     }
 
-    public Point getAnchorPosition() {
-        Point p = new Point(figureWidget.getFigure().getPosition());
-        Point p2 = slot.getRelativePosition();
-        p.translate(p2.x, p2.y);
-        return p;
-    }
-
-    protected void init() {
-
-        Point p = calculateRelativeLocation();
-        Rectangle r = calculateClientArea();
-        p = new Point(p.x, p.y - r.height / 2);
-        this.setPreferredLocation(p);
+    @Override
+    protected void notifyStateChanged(ObjectState previousState, ObjectState state) {
+        super.notifyStateChanged(previousState, state);
+        repaint();
     }
 
     public Slot getSlot() {
@@ -84,43 +80,98 @@
     @Override
     protected void paintWidget() {
 
-        if (scene.getRealZoomFactor() < ZOOM_FACTOR) {
+        if (getScene().getZoomFactor() < ZOOM_FACTOR) {
             return;
         }
 
-        if (bufferImage == null) {
-            Graphics2D g = this.getGraphics();
-            g.setColor(Color.DARK_GRAY);
-            int w = this.getBounds().width;
-            int h = this.getBounds().height;
+        Graphics2D g = this.getGraphics();
+        // g.setColor(Color.DARK_GRAY);
+        int w = this.getBounds().width;
+        int h = this.getBounds().height;
+
+        if (getSlot().getSource().getSourceNodes().size() > 0) {
+            final int SMALLER = 0;
+            g.setColor(getSlot().getColor());
+
+            int FONT_OFFSET = 2;
+
+            int s = h - SMALLER;
+            int rectW = s;
+
+            Font font = this.getSlot().getFigure().getDiagram().getSlotFont();
+            if (this.getState().isSelected()) {
+                font = font.deriveFont(Font.BOLD);
+            }
+
+            if (getSlot().getShortName() != null && getSlot().getShortName().length() > 0) {
+                g.setFont(font);
+                Rectangle2D r1 = g.getFontMetrics().getStringBounds(getSlot().getShortName(), g);
+                rectW = (int) r1.getWidth() + FONT_OFFSET * 2;
+            }
+            g.fillRect(w / 2 - rectW / 2, 0, rectW - 1, s - 1);
 
-            if (getSlot().getShortName() != null && getSlot().getShortName().length() > 0 && scene.getRealZoomFactor() >= TEXT_ZOOM_FACTOR) {
-                Font f = new Font("Arial", Font.PLAIN, 8);
-                g.setFont(f.deriveFont(7.5f));
-                Rectangle2D r1 = g.getFontMetrics().getStringBounds(getSlot().getShortName(), g);
-                g.drawString(getSlot().getShortName(), (int) (this.getBounds().width - r1.getWidth()) / 2, (int) (this.getBounds().height + r1.getHeight()) / 2);
+            if (this.getState().isHighlighted()) {
+                g.setColor(Color.BLUE);
             } else {
+                g.setColor(Color.BLACK);
+            }
+            g.drawRect(w / 2 - rectW / 2, 0, rectW - 1, s - 1);
 
+            if (getSlot().getShortName() != null && getSlot().getShortName().length() > 0 && getScene().getZoomFactor() >= TEXT_ZOOM_FACTOR) {
+                Rectangle2D r1 = g.getFontMetrics().getStringBounds(getSlot().getShortName(), g);
+                g.drawString(getSlot().getShortName(), (int) (w - r1.getWidth()) / 2, g.getFontMetrics().getAscent() - 1);//(int) (r1.getHeight()));
+            }
+
+        } else {
+
+            if (this.getSlot().getConnections().isEmpty()) {
+                if (this.getState().isHighlighted()) {
+                    g.setColor(Color.BLUE);
+                } else {
+                    g.setColor(Color.BLACK);
+                }
+                int r = 2;
                 if (slot instanceof OutputSlot) {
-                    g.fillArc(w / 4, -h / 4 - 1, w / 2, h / 2, 180, 180);
+                    g.fillOval(w / 2 - r, Figure.SLOT_WIDTH - Figure.SLOT_START - r, 2 * r, 2 * r);
                 } else {
-                    g.fillArc(w / 4, 3 * h / 4, w / 2, h / 2, 0, 180);
+                    g.fillOval(w / 2 - r, Figure.SLOT_START - r, 2 * r, 2 * r);
                 }
+            } else {
+                // Do not paint a slot with connections.
             }
         }
     }
 
     @Override
     protected Rectangle calculateClientArea() {
-        return new Rectangle(0, 0, Figure.SLOT_WIDTH, Figure.SLOT_WIDTH);
+        return new Rectangle(0, 0, slot.getWidth(), Figure.SLOT_WIDTH);
+    }
+
+    protected abstract int calculateSlotWidth();
+
+    protected int calculateWidth(int count) {
+        return getFigureWidget().getFigure().getWidth() / count;
     }
 
-    protected abstract Point calculateRelativeLocation();
+    @Override
+    public void handleDoubleClick(Widget w, WidgetAction.WidgetMouseEvent e) {
+        Set<Integer> hiddenNodes = new HashSet<>(diagramScene.getModel().getHiddenNodes());
+        if (diagramScene.isAllVisible()) {
+            hiddenNodes = new HashSet<>(diagramScene.getModel().getGraphToView().getGroup().getAllNodes());
+        }
 
-    protected double calculateRelativeY(int size, int index) {
-        assert index >= 0 && index < size;
-        assert size > 0;
-        double height = getFigureWidget().getBounds().getHeight();
-        return height * (index + 1) / (size + 1);
+        boolean progress = false;
+        for (Figure f : diagramScene.getModel().getDiagramToView().getFigures()) {
+            for (Slot s : f.getSlots()) {
+                if (DiagramScene.doesIntersect(s.getSource().getSourceNodesAsSet(), slot.getSource().getSourceNodesAsSet())) {
+                    progress = true;
+                    hiddenNodes.removeAll(f.getSource().getSourceNodesAsSet());
+                }
+            }
+        }
+
+        if (progress) {
+            this.diagramScene.getModel().showNot(hiddenNodes);
+        }
     }
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/branding.jnlp	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,15 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE jnlp PUBLIC "-//Sun Microsystems, Inc//DTD JNLP Descriptor 6.0//EN" "http://java.sun.com/dtd/JNLP-6.0.dtd">
+<jnlp spec="1.0+" codebase="$$codebase">
+  <information>
+      <title>${app.title}</title>
+      <vendor>${app.title} vendor</vendor>
+      <description>${app.name} application</description>
+      <icon href="${app.icon}"/>
+  </information>
+  ${jnlp.permissions}
+  <resources>
+    ${jnlp.branding.jars}
+  </resources>
+  <component-desc/>
+</jnlp>  
--- a/hotspot/src/share/tools/IdealGraphVisualizer/branding/core/core.jar/org/netbeans/core/startup/Bundle.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/branding/core/core.jar/org/netbeans/core/startup/Bundle.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,7 +1,7 @@
 currentVersion=IdealGraphVisualizer {0}
 LBL_splash_window_title=Starting IdealGraphVisualizer
 SPLASH_WIDTH=475
-SplashProgressBarBounds=0,268,473,6
+SplashProgressBarBounds=0,273,475,6
 SplashProgressBarColor=0xFFFFFF
-SplashRunningTextBounds=269,253,205,12
+SplashRunningTextBounds=10,283,460,12
 SplashRunningTextColor=0xFFFFFF
Binary file hotspot/src/share/tools/IdealGraphVisualizer/branding/core/core.jar/org/netbeans/core/startup/frame.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/branding/core/core.jar/org/netbeans/core/startup/frame32.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/branding/core/core.jar/org/netbeans/core/startup/frame48.gif has changed
Binary file hotspot/src/share/tools/IdealGraphVisualizer/branding/core/core.jar/org/netbeans/core/startup/splash.gif has changed
--- a/hotspot/src/share/tools/IdealGraphVisualizer/branding/modules/org-netbeans-core-windows.jar/org/netbeans/core/windows/view/ui/Bundle.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/branding/modules/org-netbeans-core-windows.jar/org/netbeans/core/windows/view/ui/Bundle.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,2 +1,2 @@
-CTL_MainWindow_Title=IdealGraphVisualizer {0}
-CTL_MainWindow_Title_No_Project=IdealGraphVisualizer {0}
+CTL_MainWindow_Title=IdealGraphVisualizer
+CTL_MainWindow_Title_No_Project=IdealGraphVisualizer
--- a/hotspot/src/share/tools/IdealGraphVisualizer/build.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/build.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -5,4 +5,12 @@
 <project name="IdealGraphVisualizer" basedir=".">
     <description>Builds the module suite IdealGraphVisualizer.</description>
     <import file="nbproject/build-impl.xml"/>
+    
+    <target name="build-launchers" depends="suite.build-launchers">
+        <!-- Drop memory presets (-Xms, -Xmx) from default_options of packaged builds and let the executing VM choose reasonable defaults -->
+        <replaceregexp file="${build.launcher.dir}/etc/${app.name}.conf" byline="true" match="^default_options=.*" replace='default_options="--branding idealgraphvisualizer"' />
+    </target>
+    
+    <!-- Local (environment-specific) extensions/modifications to the build -->
+    <import file="build-local.xml" optional="true" />
 </project>
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/igv.sh	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,23 @@
+#!/bin/sh
+# 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.
+ant run >.igv.log 2>&1
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/master.jnlp	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,25 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE jnlp PUBLIC "-//Sun Microsystems, Inc//DTD JNLP Descriptor 6.0//EN" "http://java.sun.com/dtd/JNLP-6.0.dtd">
+<jnlp spec="1.0+" codebase="$$codebase" href="master.jnlp">
+  <information>
+      <title>Ideal Graph Visualizer</title>
+      <vendor>Ideal Graph Visualizer Team</vendor>
+      <description>A graph visualization tool designed for analyzing evolving compiler graphs. It was originally designed for the ideal graph in the HotSpot server compiler, but can be used to visualize arbitrary graph data structures.</description>
+      <icon href="${app.icon}"/>
+  </information>
+  <security><all-permissions/></security>
+  <resources>
+    <!-- The following property is needed when running with unsigned jars: -->
+    <property name="netbeans.jnlp.fixPolicy" value="${netbeans.jnlp.fixPolicy}"/>
+    <extension name='branding' href='branding.jnlp' />
+<!-- The following line will be replaced with an automatically generated list of resources: -->
+<!--${jnlp.resources}-->
+  </resources>
+  <resources os="Mac OS X">
+      <property name="netbeans.user" value="${user.home}/Library/Application Support/${app.name}"/>
+  </resources>
+  <application-desc>
+    <argument>--branding</argument>
+    <argument>${branding.token}</argument>
+  </application-desc>
+</jnlp>  
--- a/hotspot/src/share/tools/IdealGraphVisualizer/nbproject/build-impl.xml	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/nbproject/build-impl.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -4,6 +4,13 @@
 ***         EDIT ../build.xml INSTEAD         ***
 -->
 <project name="IdealGraphVisualizer-impl" basedir=".." xmlns:sproject="http://www.netbeans.org/ns/nb-module-suite-project/1">
+    <fail message="Please build using Ant 1.7.1 or higher.">
+        <condition>
+            <not>
+                <antversion atleast="1.7.1"/>
+            </not>
+        </condition>
+    </fail>
     <property file="nbproject/private/platform-private.properties"/>
     <property file="nbproject/platform.properties"/>
     <macrodef name="property" uri="http://www.netbeans.org/ns/nb-module-suite-project/1">
@@ -13,13 +20,29 @@
             <property name="@{name}" value="${@{value}}"/>
         </sequential>
     </macrodef>
+    <macrodef name="evalprops" uri="http://www.netbeans.org/ns/nb-module-suite-project/1">
+        <attribute name="property"/>
+        <attribute name="value"/>
+        <sequential>
+            <property name="@{property}" value="@{value}"/>
+        </sequential>
+    </macrodef>
     <property file="${user.properties.file}"/>
     <sproject:property name="harness.dir" value="nbplatform.${nbplatform.active}.harness.dir"/>
-    <sproject:property name="netbeans.dest.dir" value="nbplatform.${nbplatform.active}.netbeans.dest.dir"/>
-    <fail message="You must define 'nbplatform.${nbplatform.active}.harness.dir'">
+    <sproject:property name="nbplatform.active.dir" value="nbplatform.${nbplatform.active}.netbeans.dest.dir"/>
+    <sproject:evalprops property="cluster.path.evaluated" value="${cluster.path}"/>
+    <fail message="Path to 'platform' cluster missing in $${cluster.path} property or using corrupt Netbeans Platform (missing harness).">
         <condition>
             <not>
-                <available file="${harness.dir}" type="dir"/>
+                <contains string="${cluster.path.evaluated}" substring="platform"/>
+            </not>
+        </condition>
+    </fail>
+    <ant antfile="nbproject/platform.xml"/>
+    <fail message="Cannot find NetBeans build harness. ${line.separator}Check that nbplatform.${nbplatform.active}.netbeans.dest.dir and nbplatform.${nbplatform.active}.harness.dir are defined. ${line.separator}On a developer machine these are normally defined in ${user.properties.file}=${netbeans.user}/build.properties ${line.separator}but for automated builds you should pass these properties to Ant explicitly. ${line.separator}You may instead download the harness and platform: -Dbootstrap.url=.../tasks.jar -Dautoupdate.catalog.url=.../updates.xml">
+        <condition>
+            <not>
+                <available file="${harness.dir}/suite.xml"/>
             </not>
         </condition>
     </fail>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/nbproject/genfiles.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/nbproject/genfiles.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,8 +1,11 @@
-build.xml.data.CRC32=72833581
-build.xml.script.CRC32=e9c757c5
-build.xml.stylesheet.CRC32=531c622b
+build.xml.data.CRC32=3c2c6126
+build.xml.script.CRC32=48934e60
+build.xml.stylesheet.CRC32=eaf9f76a@1.45.1
 # This file is used by a NetBeans-based IDE to track changes in generated files such as build-impl.xml.
 # Do not edit this file. You may delete it but then the IDE will never regenerate such files for you.
-nbproject/build-impl.xml.data.CRC32=72833581
-nbproject/build-impl.xml.script.CRC32=1b6f3648
-nbproject/build-impl.xml.stylesheet.CRC32=196c7090
+nbproject/build-impl.xml.data.CRC32=3c2c6126
+nbproject/build-impl.xml.script.CRC32=b26e57e5
+nbproject/build-impl.xml.stylesheet.CRC32=0f381476@2.62.1
+nbproject/platform.xml.data.CRC32=3c2c6126
+nbproject/platform.xml.script.CRC32=6dcbd131
+nbproject/platform.xml.stylesheet.CRC32=4e1f53d4@2.62.1
--- a/hotspot/src/share/tools/IdealGraphVisualizer/nbproject/platform.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/nbproject/platform.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,29 +1,18 @@
-# Deprecated since 5.0u1; for compatibility with 5.0:
-disabled.clusters=\
-    apisupport1,\
-    gsf1,\
-    harness,\
-    ide9,\
-    java2,\
-    nb6.1,\
-    profiler3
-disabled.modules=\
-    org.netbeans.core.execution,\
-    org.netbeans.core.multiview,\
-    org.netbeans.core.output2,\
-    org.netbeans.modules.autoupdate.services,\
-    org.netbeans.modules.autoupdate.ui,\
-    org.netbeans.modules.core.kit,\
-    org.netbeans.modules.favorites,\
-    org.netbeans.modules.javahelp,\
-    org.netbeans.modules.masterfs,\
-    org.netbeans.modules.options.keymap,\
-    org.netbeans.modules.sendopts,\
-    org.netbeans.modules.templates,\
-    org.openide.compat,\
-    org.openide.execution,\
-    org.openide.util.enumerations
-enabled.clusters=\
-    platform8
-nbjdk.active=default
+branding.token=idealgraphvisualizer
+cluster.path=\
+    ${nbplatform.active.dir}/ide:\
+    ${nbplatform.active.dir}/platform
+disabled.modules=
+nbplatform.active.dir=${suite.dir}/nbplatform
+nbplatform.default.netbeans.dest.dir=${suite.dir}/nbplatform
+nbplatform.default.harness.dir=${nbplatform.default.netbeans.dest.dir}/harness
+bootstrap.url=http://deadlock.netbeans.org/hudson/job/nbms-and-javadoc/lastSuccessfulBuild/artifact/nbbuild/netbeans/harness/tasks.jar
+autoupdate.catalog.url=http://updates.netbeans.org/netbeans/updates/7.4/uc/final/distribution/catalog.xml.gz
+suite.dir=${basedir}
 nbplatform.active=default
+## Not disabled because of NetBeans bug 206347:
+## Applications not using OSGi don't start on NbP 7.1
+#   org.netbeans.core.netigso,\
+#   org.netbeans.libs.felix,\
+#   org.netbeans.libs.osgi,\
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/nbproject/platform.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project name="platform" default="download" basedir="..">
+    <condition property="download.required">
+        <and>
+            <not>
+                <available file="${harness.dir}/suite.xml"/>
+            </not>
+            <isset property="bootstrap.url"/>
+            <isset property="autoupdate.catalog.url"/>
+        </and>
+    </condition>
+    <target name="download" if="download.required">
+        <mkdir dir="${harness.dir}"/>
+        <pathconvert pathsep="|" property="download.clusters">
+            <mapper type="flatten"/>
+            <path path="${cluster.path}"/>
+        </pathconvert>
+        <property name="disabled.modules" value=""/>
+        <pathconvert property="module.includes" pathsep="">
+            <mapper type="glob" from="${basedir}${file.separator}*" to="(?!^\Q*\E$)"/>
+            <path>
+                <filelist files="${disabled.modules}" dir="."/>
+            </path>
+        </pathconvert>
+        <echo message="Downloading clusters ${download.clusters}"/>
+        <property name="tasks.jar" location="${java.io.tmpdir}/tasks.jar"/>
+        <get src="${bootstrap.url}" dest="${tasks.jar}" usetimestamp="true" verbose="true"/>
+        <taskdef name="autoupdate" classname="org.netbeans.nbbuild.AutoUpdate" classpath="${tasks.jar}"/>
+        <autoupdate installdir="${nbplatform.active.dir}" updatecenter="${autoupdate.catalog.url}">
+            <modules includes="${module.includes}.*" clusters="${download.clusters}"/>
+            <modules includes="org[.]netbeans[.]modules[.]apisupport[.]harness" clusters="harness"/>
+        </autoupdate>
+    </target>
+</project>
--- a/hotspot/src/share/tools/IdealGraphVisualizer/nbproject/project.properties	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/IdealGraphVisualizer/nbproject/project.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -1,7 +1,13 @@
 app.icon=branding/core/core.jar/org/netbeans/core/startup/frame48.gif
-app.name=idealgraphvisualizer
+app.name=${branding.token}
 app.title=IdealGraphVisualizer
-branding.token=${app.name}
+auxiliary.org-netbeans-modules-apisupport-installer.license-type=no
+auxiliary.org-netbeans-modules-apisupport-installer.os-linux=false
+auxiliary.org-netbeans-modules-apisupport-installer.os-macosx=true
+auxiliary.org-netbeans-modules-apisupport-installer.os-solaris=false
+auxiliary.org-netbeans-modules-apisupport-installer.os-windows=false
+auxiliary.org-netbeans-modules-apisupport-installer.pack200-enabled=false
+auxiliary.org-netbeans-spi-editor-hints-projects.perProjectHintSettingsFile=nbproject/cfg_hints.xml
 modules=\
     ${project.com.sun.hotspot.igv.graph}:\
     ${project.com.sun.hotspot.igv.coordinator}:\
@@ -18,7 +24,9 @@
     ${project.com.sun.hotspot.igv.svg}:\
     ${project.com.sun.hotspot.connection}:\
     ${project.com.sun.hotspot.igv.servercompilerscheduler}:\
-    ${project.com.sun.hotspot.igv.filterwindow}
+    ${project.com.sun.hotspot.igv.filterwindow}:\
+    ${project.com.sun.hotspot.igv.selectioncoordinator}:\
+    ${project.com.sun.hotspot.igv.graal}
 project.com.sun.hotspot.connection=NetworkConnection
 project.com.sun.hotspot.igv.bytecodes=Bytecodes
 project.com.sun.hotspot.igv.controlflow=ControlFlow
@@ -27,13 +35,18 @@
 project.com.sun.hotspot.igv.difference=Difference
 project.com.sun.hotspot.igv.filter=Filter
 project.com.sun.hotspot.igv.filterwindow=FilterWindow
+project.com.sun.hotspot.igv.graal=Graal
 project.com.sun.hotspot.igv.graph=Graph
 project.com.sun.hotspot.igv.hierarchicallayout=HierarchicalLayout
 project.com.sun.hotspot.igv.layout=Layout
+project.com.sun.hotspot.igv.selectioncoordinator=SelectionCoordinator
 project.com.sun.hotspot.igv.servercompilerscheduler=ServerCompiler
 project.com.sun.hotspot.igv.settings=Settings
 project.com.sun.hotspot.igv.svg=BatikSVGProxy
 project.com.sun.hotspot.igv.view=View
 project.com.sun.hotspot.igv.util=Util
-run.args = -J-server -J-Xms64m -J-Xmx1g -J-da
-run.args.extra = -J-server -J-Xms64m -J-Xmx1g -J-da
+
+# Disable assertions for RequestProcessor to prevent annoying messages in case
+# of multiple SceneAnimator update tasks in the default RequestProcessor.
+run.args.extra = -J-server -J-da:org.openide.util.RequestProcessor -J-Xms2g -J-Xmx8g -J-Djava.lang.Integer.IntegerCache.high=20000
+debug.args.extra = -J-server -J-da:org.openide.util.RequestProcessor
--- a/hotspot/src/share/tools/ProjectCreator/WinGammaPlatformVC10.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/tools/ProjectCreator/WinGammaPlatformVC10.java	Wed Jul 05 20:35:10 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
@@ -81,6 +81,7 @@
             startTag(cfg, "PropertyGroup", "Label", "Configuration");
             tagData("ConfigurationType", "DynamicLibrary");
             tagData("UseOfMfc", "false");
+            tagData("PlatformToolset", "v120");
             endTag();
         }
 
--- a/hotspot/src/share/vm/adlc/archDesc.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/adlc/archDesc.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -929,6 +929,7 @@
     case 'D':  return "TypeVect::VECTD";
     case 'X':  return "TypeVect::VECTX";
     case 'Y':  return "TypeVect::VECTY";
+    case 'Z':  return "TypeVect::VECTZ";
     default:
       internal_err("Vector type %s with unrecognized type\n",idealOp);
     }
--- a/hotspot/src/share/vm/adlc/formssel.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/adlc/formssel.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -3919,6 +3919,7 @@
          strcmp(opType,"VecD")==0 ||
          strcmp(opType,"VecX")==0 ||
          strcmp(opType,"VecY")==0 ||
+         strcmp(opType,"VecZ")==0 ||
          strcmp(opType,"Reg" )==0) ) {
       return 1;
     }
@@ -4048,6 +4049,7 @@
         strcmp(opType,"AddReductionVF")==0 ||
         strcmp(opType,"AddReductionVD")==0 ||
         strcmp(opType,"MulReductionVI")==0 ||
+        strcmp(opType,"MulReductionVL")==0 ||
         strcmp(opType,"MulReductionVF")==0 ||
         strcmp(opType,"MulReductionVD")==0 ||
         0 /* 0 to line up columns nicely */ )
@@ -4139,12 +4141,12 @@
   static const char *vector_list[] = {
     "AddVB","AddVS","AddVI","AddVL","AddVF","AddVD",
     "SubVB","SubVS","SubVI","SubVL","SubVF","SubVD",
-    "MulVS","MulVI","MulVF","MulVD",
+    "MulVS","MulVI","MulVL","MulVF","MulVD",
     "DivVF","DivVD",
     "AndV" ,"XorV" ,"OrV",
     "AddReductionVI", "AddReductionVL",
     "AddReductionVF", "AddReductionVD",
-    "MulReductionVI",
+    "MulReductionVI", "MulReductionVL",
     "MulReductionVF", "MulReductionVD",
     "LShiftCntV","RShiftCntV",
     "LShiftVB","LShiftVS","LShiftVI","LShiftVL",
--- a/hotspot/src/share/vm/c1/c1_LinearScan.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/c1/c1_LinearScan.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1290,7 +1290,8 @@
 #ifdef X86
     }
     if (UseSSE > 0) {
-      for (i = 0; i < FrameMap::nof_caller_save_xmm_regs; i++) {
+      int num_caller_save_xmm_regs = FrameMap::get_num_caller_save_xmms();
+      for (i = 0; i < num_caller_save_xmm_regs; i ++) {
         LIR_Opr opr = FrameMap::caller_save_xmm_reg_at(i);
         assert(opr->is_valid() && opr->is_register(), "FrameMap should not return invalid operands");
         assert(reg_numHi(opr) == -1, "missing addition of range for hi-register");
@@ -2098,7 +2099,13 @@
       case T_FLOAT: {
 #ifdef X86
         if (UseSSE >= 1) {
-          assert(assigned_reg >= pd_first_xmm_reg && assigned_reg <= pd_last_xmm_reg, "no xmm register");
+          int last_xmm_reg = pd_last_xmm_reg;
+#ifdef _LP64
+          if (UseAVX < 3) {
+            last_xmm_reg = pd_first_xmm_reg + (pd_nof_xmm_regs_frame_map / 2) - 1;
+          }
+#endif
+          assert(assigned_reg >= pd_first_xmm_reg && assigned_reg <= last_xmm_reg, "no xmm register");
           assert(interval->assigned_regHi() == any_reg, "must not have hi register");
           return LIR_OprFact::single_xmm(assigned_reg - pd_first_xmm_reg);
         }
@@ -2112,7 +2119,13 @@
       case T_DOUBLE: {
 #ifdef X86
         if (UseSSE >= 2) {
-          assert(assigned_reg >= pd_first_xmm_reg && assigned_reg <= pd_last_xmm_reg, "no xmm register");
+          int last_xmm_reg = pd_last_xmm_reg;
+#ifdef _LP64
+          if (UseAVX < 3) {
+            last_xmm_reg = pd_first_xmm_reg + (pd_nof_xmm_regs_frame_map / 2) - 1;
+          }
+#endif
+          assert(assigned_reg >= pd_first_xmm_reg && assigned_reg <= last_xmm_reg, "no xmm register");
           assert(interval->assigned_regHi() == any_reg, "must not have hi register (double xmm values are stored in one register)");
           return LIR_OprFact::double_xmm(assigned_reg - pd_first_xmm_reg);
         }
@@ -3600,7 +3613,8 @@
       }
 
 #ifdef X86
-      for (j = 0; j < FrameMap::nof_caller_save_xmm_regs; j++) {
+      int num_caller_save_xmm_regs = FrameMap::get_num_caller_save_xmms();
+      for (j = 0; j < num_caller_save_xmm_regs; j++) {
         state_put(input_state, reg_num(FrameMap::caller_save_xmm_reg_at(j)), NULL);
       }
 #endif
@@ -4514,12 +4528,20 @@
   if (reg_num() < LIR_OprDesc::vreg_base) {
     type_name = "fixed";
     // need a temporary operand for fixed intervals because type() cannot be called
+#ifdef X86
+    int last_xmm_reg = pd_last_xmm_reg;
+#ifdef _LP64
+    if (UseAVX < 3) {
+      last_xmm_reg = pd_first_xmm_reg + (pd_nof_xmm_regs_frame_map / 2) - 1;
+    }
+#endif
+#endif
     if (assigned_reg() >= pd_first_cpu_reg && assigned_reg() <= pd_last_cpu_reg) {
       opr = LIR_OprFact::single_cpu(assigned_reg());
     } else if (assigned_reg() >= pd_first_fpu_reg && assigned_reg() <= pd_last_fpu_reg) {
       opr = LIR_OprFact::single_fpu(assigned_reg() - pd_first_fpu_reg);
 #ifdef X86
-    } else if (assigned_reg() >= pd_first_xmm_reg && assigned_reg() <= pd_last_xmm_reg) {
+    } else if (assigned_reg() >= pd_first_xmm_reg && assigned_reg() <= last_xmm_reg) {
       opr = LIR_OprFact::single_xmm(assigned_reg() - pd_first_xmm_reg);
 #endif
     } else {
--- a/hotspot/src/share/vm/c1/c1_Runtime1.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/c1/c1_Runtime1.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1018,7 +1018,7 @@
           // NOTE we use pc() not original_pc() because we already know they are
           // identical otherwise we'd have never entered this block of code
 
-          OopMap* map = caller_code->oop_map_for_return_address(caller_frame.pc());
+          const ImmutableOopMap* map = caller_code->oop_map_for_return_address(caller_frame.pc());
           assert(map != NULL, "null check");
           map->print();
           tty->cr();
--- a/hotspot/src/share/vm/classfile/verificationType.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/classfile/verificationType.cpp	Wed Jul 05 20:35:10 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
@@ -61,6 +61,10 @@
     Klass* obj = SystemDictionary::resolve_or_fail(
         name(), Handle(THREAD, klass->class_loader()),
         Handle(THREAD, klass->protection_domain()), true, CHECK_false);
+    if (TraceClassResolution) {
+      Verifier::trace_class_resolution(obj, klass());
+    }
+
     KlassHandle this_class(THREAD, obj);
 
     if (this_class->is_interface() && (!from_field_is_protected ||
@@ -73,6 +77,9 @@
       Klass* from_class = SystemDictionary::resolve_or_fail(
           from.name(), Handle(THREAD, klass->class_loader()),
           Handle(THREAD, klass->protection_domain()), true, CHECK_false);
+      if (TraceClassResolution) {
+        Verifier::trace_class_resolution(from_class, klass());
+      }
       return InstanceKlass::cast(from_class)->is_subclass_of(this_class());
     }
   } else if (is_array() && from.is_array()) {
--- a/hotspot/src/share/vm/classfile/verifier.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/classfile/verifier.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -94,6 +94,21 @@
   return !need_verify;
 }
 
+void Verifier::trace_class_resolution(Klass* resolve_class, InstanceKlass* verify_class) {
+  assert(verify_class != NULL, "Unexpected null verify_class");
+  ResourceMark rm;
+  Symbol* s = verify_class->source_file_name();
+  const char* source_file = (s != NULL ? s->as_C_string() : NULL);
+  const char* verify = verify_class->external_name();
+  const char* resolve = resolve_class->external_name();
+  // print in a single call to reduce interleaving between threads
+  if (source_file != NULL) {
+    tty->print("RESOLVE %s %s %s (verification)\n", verify, resolve, source_file);
+  } else {
+    tty->print("RESOLVE %s %s (verification)\n", verify, resolve);
+  }
+}
+
 bool Verifier::verify(instanceKlassHandle klass, Verifier::Mode mode, bool should_verify_class, TRAPS) {
   HandleMark hm;
   ResourceMark rm(THREAD);
@@ -172,6 +187,10 @@
     ResourceMark rm(THREAD);
     instanceKlassHandle kls =
       SystemDictionary::resolve_or_fail(exception_name, true, CHECK_false);
+    if (TraceClassResolution) {
+      Verifier::trace_class_resolution(kls(), klass());
+    }
+
     while (!kls.is_null()) {
       if (kls == klass) {
         // If the class being verified is the exception we're creating
@@ -1947,9 +1966,15 @@
   oop loader = current_class()->class_loader();
   oop protection_domain = current_class()->protection_domain();
 
-  return SystemDictionary::resolve_or_fail(
+  Klass* kls = SystemDictionary::resolve_or_fail(
     name, Handle(THREAD, loader), Handle(THREAD, protection_domain),
     true, THREAD);
+
+  if (TraceClassResolution) {
+    instanceKlassHandle cur_class = current_class();
+    Verifier::trace_class_resolution(kls, cur_class());
+  }
+  return kls;
 }
 
 bool ClassVerifier::is_protected_access(instanceKlassHandle this_class,
--- a/hotspot/src/share/vm/classfile/verifier.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/classfile/verifier.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -60,6 +60,9 @@
   // Relax certain verifier checks to enable some broken 1.1 apps to run on 1.2.
   static bool relax_verify_for(oop class_loader);
 
+  // Print output for -XX:+TraceClassResolution
+  static void trace_class_resolution(Klass* resolve_class, InstanceKlass* verify_class);
+
  private:
   static bool is_eligible_for_verification(instanceKlassHandle klass, bool should_verify_class);
   static Symbol* inference_verify(
--- a/hotspot/src/share/vm/classfile/vmSymbols.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/classfile/vmSymbols.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -591,6 +591,9 @@
   template(classLoader_name,                           "classLoader")                                             \
   template(componentType_name,                         "componentType")                                           \
                                                                                                                   \
+  /* forEachRemaining support */                                                                                  \
+  template(java_util_stream_StreamsRangeIntSpliterator,          "java/util/stream/Streams$RangeIntSpliterator")  \
+                                                                                                                  \
   /* trace signatures */                                                                                          \
   TRACE_TEMPLATES(template)                                                                                       \
                                                                                                                   \
@@ -1121,6 +1124,11 @@
   do_intrinsic(_Double_valueOf,           java_lang_Double,       valueOf_name, Double_valueOf_signature, F_S)          \
    do_name(     Double_valueOf_signature,                        "(D)Ljava/lang/Double;")                               \
                                                                                                                         \
+  /* forEachRemaining */                                                                             \
+  do_intrinsic(_forEachRemaining, java_util_stream_StreamsRangeIntSpliterator, forEachRemaining_name, forEachRemaining_signature, F_R) \
+   do_name(     forEachRemaining_name,    "forEachRemaining")                                                           \
+   do_name(     forEachRemaining_signature,                      "(Ljava/util/function/IntConsumer;)V")                 \
+
     /*end*/
 
 
--- a/hotspot/src/share/vm/code/codeBlob.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/code/codeBlob.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -129,9 +129,7 @@
   // Danger Will Robinson! This method allocates a big
   // chunk of memory, its your job to free it.
   if (p != NULL) {
-    // We need to allocate a chunk big enough to hold the OopMapSet and all of its OopMaps
-    _oop_maps = (OopMapSet* )NEW_C_HEAP_ARRAY(unsigned char, p->heap_size(), mtCode);
-    p->copy_to((address)_oop_maps);
+    _oop_maps = ImmutableOopMapSet::build_from(p);
   } else {
     _oop_maps = NULL;
   }
@@ -175,7 +173,7 @@
 }
 
 
-OopMap* CodeBlob::oop_map_for_return_address(address return_address) {
+const ImmutableOopMap* CodeBlob::oop_map_for_return_address(address return_address) {
   assert(oop_maps() != NULL, "nope");
   return oop_maps()->find_map_at_offset((intptr_t) return_address - (intptr_t) code_begin());
 }
--- a/hotspot/src/share/vm/code/codeBlob.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/code/codeBlob.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -77,7 +77,7 @@
                                                  // which we don't detect.
   int        _data_offset;                       // offset to where data region begins
   int        _frame_size;                        // size of stack frame
-  OopMapSet* _oop_maps;                          // OopMap for this CodeBlob
+  ImmutableOopMapSet* _oop_maps;                 // OopMap for this CodeBlob
   CodeStrings _strings;
 
  public:
@@ -171,9 +171,9 @@
   virtual bool is_alive() const                  = 0;
 
   // OopMap for frame
-  OopMapSet* oop_maps() const                    { return _oop_maps; }
+  ImmutableOopMapSet* oop_maps() const           { return _oop_maps; }
   void set_oop_maps(OopMapSet* p);
-  OopMap* oop_map_for_return_address(address return_address);
+  const ImmutableOopMap* oop_map_for_return_address(address return_address);
   virtual void preserve_callee_argument_oops(frame fr, const RegisterMap* reg_map, OopClosure* f)  { ShouldNotReachHere(); }
 
   // Frame support
--- a/hotspot/src/share/vm/code/codeCache.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/code/codeCache.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -41,6 +41,7 @@
 #include "oops/verifyOopClosure.hpp"
 #include "runtime/handles.inline.hpp"
 #include "runtime/arguments.hpp"
+#include "runtime/deoptimization.hpp"
 #include "runtime/icache.hpp"
 #include "runtime/java.hpp"
 #include "runtime/mutexLocker.hpp"
@@ -1371,10 +1372,10 @@
         if (cb->is_alive()) {
           number_of_blobs++;
           code_size += cb->code_size();
-          OopMapSet* set = cb->oop_maps();
+          ImmutableOopMapSet* set = cb->oop_maps();
           if (set != NULL) {
-            number_of_oop_maps += set->size();
-            map_size           += set->heap_size();
+            number_of_oop_maps += set->count();
+            map_size           += set->nr_of_bytes();
           }
         }
       }
--- a/hotspot/src/share/vm/code/nmethod.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/code/nmethod.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -2987,11 +2987,12 @@
   // We use the odd half-closed interval so that oop maps and scope descs
   // which are tied to the byte after a call are printed with the call itself.
   address base = code_begin();
-  OopMapSet* oms = oop_maps();
+  ImmutableOopMapSet* oms = oop_maps();
   if (oms != NULL) {
-    for (int i = 0, imax = oms->size(); i < imax; i++) {
-      OopMap* om = oms->at(i);
-      address pc = base + om->offset();
+    for (int i = 0, imax = oms->count(); i < imax; i++) {
+      const ImmutableOopMapPair* pair = oms->pair_at(i);
+      const ImmutableOopMap* om = pair->get_from(oms);
+      address pc = base + pair->pc_offset();
       if (pc > begin) {
         if (pc <= end) {
           st->move_to(column);
--- a/hotspot/src/share/vm/compiler/oopMap.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/compiler/oopMap.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -42,27 +42,18 @@
 
 // OopMapStream
 
-OopMapStream::OopMapStream(OopMap* oop_map) {
-  if(oop_map->omv_data() == NULL) {
-    _stream = new CompressedReadStream(oop_map->write_stream()->buffer());
-  } else {
-    _stream = new CompressedReadStream(oop_map->omv_data());
-  }
-  _mask = OopMapValue::type_mask_in_place;
+OopMapStream::OopMapStream(OopMap* oop_map, int oop_types_mask) {
+  _stream = new CompressedReadStream(oop_map->write_stream()->buffer());
+  _mask = oop_types_mask;
   _size = oop_map->omv_count();
   _position = 0;
   _valid_omv = false;
 }
 
-
-OopMapStream::OopMapStream(OopMap* oop_map, int oop_types_mask) {
-  if(oop_map->omv_data() == NULL) {
-    _stream = new CompressedReadStream(oop_map->write_stream()->buffer());
-  } else {
-    _stream = new CompressedReadStream(oop_map->omv_data());
-  }
+OopMapStream::OopMapStream(const ImmutableOopMap* oop_map, int oop_types_mask) {
+  _stream = new CompressedReadStream(oop_map->data_addr());
   _mask = oop_types_mask;
-  _size = oop_map->omv_count();
+  _size = oop_map->count();
   _position = 0;
   _valid_omv = false;
 }
@@ -87,7 +78,6 @@
 OopMap::OopMap(int frame_size, int arg_count) {
   // OopMaps are usually quite so small, so pick a small initial size
   set_write_stream(new CompressedWriteStream(32));
-  set_omv_data(NULL);
   set_omv_count(0);
 
 #ifdef ASSERT
@@ -102,7 +92,6 @@
   // This constructor does a deep copy
   // of the source OopMap.
   set_write_stream(new CompressedWriteStream(source->omv_count() * 2));
-  set_omv_data(NULL);
   set_omv_count(0);
   set_offset(source->offset());
 
@@ -125,25 +114,14 @@
   return new OopMap(_deep_copy_token, this);
 }
 
-
-void OopMap::copy_to(address addr) {
-  memcpy(addr,this,sizeof(OopMap));
-  memcpy(addr + sizeof(OopMap),write_stream()->buffer(),write_stream()->position());
-  OopMap* new_oop = (OopMap*)addr;
-  new_oop->set_omv_data_size(write_stream()->position());
-  new_oop->set_omv_data((unsigned char *)(addr + sizeof(OopMap)));
-  new_oop->set_write_stream(NULL);
+void OopMap::copy_data_to(address addr) const {
+  memcpy(addr, write_stream()->buffer(), write_stream()->position());
 }
 
-
 int OopMap::heap_size() const {
   int size = sizeof(OopMap);
   int align = sizeof(void *) - 1;
-  if(write_stream() != NULL) {
-    size += write_stream()->position();
-  } else {
-    size += omv_data_size();
-  }
+  size += write_stream()->position();
   // Align to a reasonable ending point
   size = ((size+align) & ~align);
   return size;
@@ -222,30 +200,6 @@
 }
 
 
-void OopMapSet::copy_to(address addr) {
-  address temp = addr;
-  int align = sizeof(void *) - 1;
-  // Copy this
-  memcpy(addr,this,sizeof(OopMapSet));
-  temp += sizeof(OopMapSet);
-  temp = (address)((intptr_t)(temp + align) & ~align);
-  // Do the needed fixups to the new OopMapSet
-  OopMapSet* new_set = (OopMapSet*)addr;
-  new_set->set_om_data((OopMap**)temp);
-  // Allow enough space for the OopMap pointers
-  temp += (om_count() * sizeof(OopMap*));
-
-  for(int i=0; i < om_count(); i++) {
-    OopMap* map = at(i);
-    map->copy_to((address)temp);
-    new_set->set(i,(OopMap*)temp);
-    temp += map->heap_size();
-  }
-  // This "locks" the OopMapSet
-  new_set->set_om_size(-1);
-}
-
-
 void OopMapSet::add_gc_map(int pc_offset, OopMap *map ) {
   assert(om_size() != -1,"Cannot grow a fixed OopMapSet");
 
@@ -334,8 +288,8 @@
   // Print oopmap and regmap
   tty->print_cr("------ ");
   CodeBlob* cb = fr->cb();
-  OopMapSet* maps = cb->oop_maps();
-  OopMap* map = cb->oop_map_for_return_address(fr->pc());
+  ImmutableOopMapSet* maps = cb->oop_maps();
+  const ImmutableOopMap* map = cb->oop_map_for_return_address(fr->pc());
   map->print();
   if( cb->is_nmethod() ) {
     nmethod* nm = (nmethod*)cb;
@@ -371,8 +325,8 @@
 
   NOT_PRODUCT(if (TraceCodeBlobStacks) trace_codeblob_maps(fr, reg_map);)
 
-  OopMapSet* maps = cb->oop_maps();
-  OopMap* map = cb->oop_map_for_return_address(fr->pc());
+  ImmutableOopMapSet* maps = cb->oop_maps();
+  const ImmutableOopMap* map = cb->oop_map_for_return_address(fr->pc());
   assert(map != NULL, "no ptr map found");
 
   // handle derived pointers first (otherwise base pointer may be
@@ -483,7 +437,7 @@
   // (we do not do update in place, since info could be overwritten)
 
   address pc = fr->pc();
-  OopMap* map  = cb->oop_map_for_return_address(pc);
+  const ImmutableOopMap* map  = cb->oop_map_for_return_address(pc);
   assert(map != NULL, "no ptr map found");
   DEBUG_ONLY(int nof_callee = 0;)
 
@@ -508,7 +462,7 @@
 
 #ifndef PRODUCT
 
-bool OopMap::has_derived_pointer() const {
+bool ImmutableOopMap::has_derived_pointer() const {
 #ifndef TIERED
   COMPILER1_PRESENT(return false);
 #endif // !TIERED
@@ -550,7 +504,6 @@
   }
 }
 
-
 void OopMapValue::print_on(outputStream* st) const {
   reg()->print_on(st);
   st->print("=");
@@ -558,6 +511,15 @@
   st->print(" ");
 }
 
+void ImmutableOopMap::print_on(outputStream* st) const {
+  OopMapValue omv;
+  st->print("ImmutableOopMap{");
+  for(OopMapStream oms(this); !oms.is_done(); oms.next()) {
+    omv = oms.current();
+    omv.print_on(st);
+  }
+  st->print("}");
+}
 
 void OopMap::print_on(outputStream* st) const {
   OopMapValue omv;
@@ -569,6 +531,20 @@
   st->print("off=%d}", (int) offset());
 }
 
+void ImmutableOopMapSet::print_on(outputStream* st) const {
+  const ImmutableOopMap* last = NULL;
+  for (int i = 0; i < _count; ++i) {
+    const ImmutableOopMapPair* pair = pair_at(i);
+    const ImmutableOopMap* map = pair->get_from(this);
+    if (map != last) {
+      st->cr();
+      map->print_on(st);
+      st->print("pc offsets: ");
+    }
+    last = map;
+    st->print("%d ", pair->pc_offset());
+  }
+}
 
 void OopMapSet::print_on(outputStream* st) const {
   int i, len = om_count();
@@ -583,6 +559,217 @@
   }
 }
 
+bool OopMap::equals(const OopMap* other) const {
+  if (other->_omv_count != _omv_count) {
+    return false;
+  }
+  if (other->write_stream()->position() != write_stream()->position()) {
+    return false;
+  }
+  if (memcmp(other->write_stream()->buffer(), write_stream()->buffer(), write_stream()->position()) != 0) {
+    return false;
+  }
+  return true;
+}
+
+const ImmutableOopMap* ImmutableOopMapSet::find_map_at_offset(int pc_offset) const {
+  ImmutableOopMapPair* pairs = get_pairs();
+  ImmutableOopMapPair* last = NULL;
+
+  for (int i = 0; i < _count; ++i) {
+    if (pairs[i].pc_offset() >= pc_offset) {
+      last = &pairs[i];
+      break;
+    }
+  }
+
+  assert(last->pc_offset() == pc_offset, "oopmap not found");
+  return last->get_from(this);
+}
+
+const ImmutableOopMap* ImmutableOopMapPair::get_from(const ImmutableOopMapSet* set) const {
+  return set->oopmap_at_offset(_oopmap_offset);
+}
+
+ImmutableOopMap::ImmutableOopMap(const OopMap* oopmap) : _count(oopmap->count()) {
+  address addr = data_addr();
+  oopmap->copy_data_to(addr);
+}
+
+class ImmutableOopMapBuilder {
+private:
+  class Mapping;
+
+private:
+  const OopMapSet* _set;
+  const OopMap* _empty;
+  const OopMap* _last;
+  int _empty_offset;
+  int _last_offset;
+  int _offset;
+  Mapping* _mapping;
+  ImmutableOopMapSet* _new_set;
+
+  /* Used for bookkeeping when building ImmutableOopMaps */
+  class Mapping : public ResourceObj {
+  public:
+    enum kind_t { OOPMAP_UNKNOWN = 0, OOPMAP_NEW = 1, OOPMAP_EMPTY = 2, OOPMAP_DUPLICATE = 3 };
+
+    kind_t _kind;
+    int _offset;
+    int _size;
+    const OopMap* _map;
+    const OopMap* _other;
+
+    Mapping() : _kind(OOPMAP_UNKNOWN), _offset(-1), _size(-1), _map(NULL) {}
+
+    void set(kind_t kind, int offset, int size, const OopMap* map = 0, const OopMap* other = 0) {
+      _kind = kind;
+      _offset = offset;
+      _size = size;
+      _map = map;
+      _other = other;
+    }
+  };
+
+public:
+  ImmutableOopMapBuilder(const OopMapSet* set) : _set(set), _new_set(NULL), _empty(NULL), _last(NULL), _empty_offset(-1), _last_offset(-1), _offset(0) {
+    _mapping = NEW_RESOURCE_ARRAY(Mapping, _set->size());
+  }
+
+  int heap_size();
+  ImmutableOopMapSet* build();
+private:
+  bool is_empty(const OopMap* map) const {
+    return map->count() == 0;
+  }
+
+  bool is_last_duplicate(const OopMap* map) {
+    if (_last != NULL && _last->count() > 0 && _last->equals(map)) {
+      return true;
+    }
+    return false;
+  }
+
+#ifdef ASSERT
+  void verify(address buffer, int size);
+#endif
+
+  bool has_empty() const {
+    return _empty_offset != -1;
+  }
+
+  int size_for(const OopMap* map) const;
+  void fill_pair(ImmutableOopMapPair* pair, const OopMap* map, int offset);
+  int fill_map(ImmutableOopMapPair* pair, const OopMap* map, int offset);
+  void fill(ImmutableOopMapSet* set, int size);
+};
+
+int ImmutableOopMapBuilder::size_for(const OopMap* map) const {
+  return align_size_up(sizeof(ImmutableOopMap) + map->data_size(), 8);
+}
+
+int ImmutableOopMapBuilder::heap_size() {
+  int base = sizeof(ImmutableOopMapSet);
+  base = align_size_up(base, 8);
+
+  // all of ours pc / offset pairs
+  int pairs = _set->size() * sizeof(ImmutableOopMapPair);
+  pairs = align_size_up(pairs, 8);
+
+  for (int i = 0; i < _set->size(); ++i) {
+    int size = 0;
+    OopMap* map = _set->at(i);
+
+    if (is_empty(map)) {
+      /* only keep a single empty map in the set */
+      if (has_empty()) {
+        _mapping[i].set(Mapping::OOPMAP_EMPTY, _empty_offset, 0, map, _empty);
+      } else {
+        _empty_offset = _offset;
+        _empty = map;
+        size = size_for(map);
+        _mapping[i].set(Mapping::OOPMAP_NEW, _offset, size, map);
+      }
+    } else if (is_last_duplicate(map)) {
+      /* if this entry is identical to the previous one, just point it there */
+      _mapping[i].set(Mapping::OOPMAP_DUPLICATE, _last_offset, 0, map, _last);
+    } else {
+      /* not empty, not an identical copy of the previous entry */
+      size = size_for(map);
+      _mapping[i].set(Mapping::OOPMAP_NEW, _offset, size, map);
+      _last_offset = _offset;
+      _last = map;
+    }
+
+    assert(_mapping[i]._map == map, "check");
+    _offset += size;
+  }
+
+  int total = base + pairs + _offset;
+  DEBUG_ONLY(total += 8);
+  return total;
+}
+
+void ImmutableOopMapBuilder::fill_pair(ImmutableOopMapPair* pair, const OopMap* map, int offset) {
+  new ((address) pair) ImmutableOopMapPair(map->offset(), offset);
+}
+
+int ImmutableOopMapBuilder::fill_map(ImmutableOopMapPair* pair, const OopMap* map, int offset) {
+  fill_pair(pair, map, offset);
+  address addr = (address) pair->get_from(_new_set); // location of the ImmutableOopMap
+
+  new (addr) ImmutableOopMap(map);
+  return align_size_up(sizeof(ImmutableOopMap) + map->data_size(), 8);
+}
+
+void ImmutableOopMapBuilder::fill(ImmutableOopMapSet* set, int sz) {
+  ImmutableOopMapPair* pairs = set->get_pairs();
+
+  for (int i = 0; i < set->count(); ++i) {
+    const OopMap* map = _mapping[i]._map;
+    ImmutableOopMapPair* pair = NULL;
+    int size = 0;
+
+    if (_mapping[i]._kind == Mapping::OOPMAP_NEW) {
+      size = fill_map(&pairs[i], map, _mapping[i]._offset);
+    } else if (_mapping[i]._kind == Mapping::OOPMAP_DUPLICATE || _mapping[i]._kind == Mapping::OOPMAP_EMPTY) {
+      fill_pair(&pairs[i], map, _mapping[i]._offset);
+    }
+
+    const ImmutableOopMap* nv = set->find_map_at_offset(map->offset());
+    assert(memcmp(map->data(), nv->data_addr(), map->data_size()) == 0, "check identity");
+  }
+}
+
+#ifdef ASSERT
+void ImmutableOopMapBuilder::verify(address buffer, int size) {
+  for (int i = 0; i < 8; ++i) {
+    assert(buffer[size - 8 + i] == (unsigned char) 0xff, "overwritten memory check");
+  }
+}
+#endif
+
+ImmutableOopMapSet* ImmutableOopMapBuilder::build() {
+  int required = heap_size();
+
+  // We need to allocate a chunk big enough to hold the ImmutableOopMapSet and all of its ImmutableOopMaps
+  address buffer = (address) NEW_C_HEAP_ARRAY(unsigned char, required, mtCode);
+  DEBUG_ONLY(memset(&buffer[required-8], 0xff, 8));
+
+  _new_set = new (buffer) ImmutableOopMapSet(_set, required);
+  fill(_new_set, required);
+
+  DEBUG_ONLY(verify(buffer, required));
+
+  return _new_set;
+}
+
+ImmutableOopMapSet* ImmutableOopMapSet::build_from(const OopMapSet* oopmap_set) {
+  ResourceMark mark;
+  ImmutableOopMapBuilder builder(oopmap_set);
+  return builder.build();
+}
 
 
 //------------------------------DerivedPointerTable---------------------------
--- a/hotspot/src/share/vm/compiler/oopMap.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/compiler/oopMap.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -143,19 +143,13 @@
   friend class OopMapStream;
   friend class VMStructs;
  private:
-  int  _pc_offset;
-  int  _omv_count;
-  int  _omv_data_size;
-  unsigned char* _omv_data;
+  int  _pc_offset; // offset in the code that this OopMap corresponds to
+  int  _omv_count; // number of OopMapValues in the stream
   CompressedWriteStream* _write_stream;
 
   debug_only( OopMapValue::oop_types* _locs_used; int _locs_length;)
 
   // Accessors
-  unsigned char* omv_data() const             { return _omv_data; }
-  void set_omv_data(unsigned char* value)     { _omv_data = value; }
-  int omv_data_size() const                   { return _omv_data_size; }
-  void set_omv_data_size(int value)           { _omv_data_size = value; }
   int omv_count() const                       { return _omv_count; }
   void set_omv_count(int value)               { _omv_count = value; }
   void increment_count()                      { _omv_count++; }
@@ -172,6 +166,9 @@
   // pc-offset handling
   int offset() const     { return _pc_offset; }
   void set_offset(int o) { _pc_offset = o; }
+  int count() const { return _omv_count; }
+  int data_size() const  { return write_stream()->position(); }
+  address data() const { return write_stream()->buffer(); }
 
   // Check to avoid double insertion
   debug_only(OopMapValue::oop_types locs_used( int indx ) { return _locs_used[indx]; })
@@ -188,11 +185,9 @@
   void set_xxx(VMReg reg, OopMapValue::oop_types x, VMReg optional);
 
   int heap_size() const;
-  void copy_to(address addr);
+  void copy_data_to(address addr) const;
   OopMap* deep_copy();
 
-  bool has_derived_pointer() const PRODUCT_RETURN0;
-
   bool legal_vm_reg_name(VMReg local) {
      return OopMapValue::legal_vm_reg_name(local);
   }
@@ -200,6 +195,7 @@
   // Printing
   void print_on(outputStream* st) const;
   void print() const { print_on(tty); }
+  bool equals(const OopMap* other) const;
 };
 
 
@@ -239,7 +235,6 @@
   OopMap* find_map_at_offset(int pc_offset) const;
 
   int heap_size() const;
-  void copy_to(address addr);
 
   // Methods oops_do() and all_do() filter out NULL oops and
   // oop == Universe::narrow_oop_base() before passing oops
@@ -261,6 +256,79 @@
   void print() const { print_on(tty); }
 };
 
+class ImmutableOopMapBuilder;
+
+class ImmutableOopMap {
+  friend class OopMapStream;
+  friend class VMStructs;
+#ifdef ASSERT
+  friend class ImmutableOopMapBuilder;
+#endif
+private:
+  int _count; // contains the number of entries in this OopMap
+
+  address data_addr() const { return (address) this + sizeof(ImmutableOopMap); }
+public:
+  ImmutableOopMap(const OopMap* oopmap);
+
+  bool has_derived_pointer() const PRODUCT_RETURN0;
+  int count() const { return _count; }
+
+  // Printing
+  void print_on(outputStream* st) const;
+  void print() const { print_on(tty); }
+};
+
+class ImmutableOopMapSet;
+class ImmutableOopMap;
+class OopMapSet;
+
+class ImmutableOopMapPair {
+  friend class VMStructs;
+private:
+  int _pc_offset; // program counter offset from the beginning of the method
+  int _oopmap_offset; // offset in the data in the ImmutableOopMapSet where the ImmutableOopMap is located
+public:
+  ImmutableOopMapPair(int pc_offset, int oopmap_offset) : _pc_offset(pc_offset), _oopmap_offset(oopmap_offset) {
+    assert(pc_offset >= 0 && oopmap_offset >= 0, "check");
+  }
+  const ImmutableOopMap* get_from(const ImmutableOopMapSet* set) const;
+
+  int pc_offset() const { return _pc_offset; }
+  int oopmap_offset() const { return _oopmap_offset; }
+};
+
+class ImmutableOopMapSet {
+  friend class VMStructs;
+private:
+  int _count; // nr of ImmutableOopMapPairs in the Set
+  int _size; // nr of bytes including ImmutableOopMapSet itself
+
+  address data() const { return (address) this + sizeof(*this) + sizeof(ImmutableOopMapPair) * _count; }
+
+public:
+  ImmutableOopMapSet(const OopMapSet* oopmap_set, int size) : _count(oopmap_set->size()), _size(size) {}
+
+  ImmutableOopMap* oopmap_at_offset(int offset) const {
+    assert(offset >= 0 && offset < _size, "must be within boundaries");
+    address addr = data() + offset;
+    return (ImmutableOopMap*) addr;
+  }
+
+  ImmutableOopMapPair* get_pairs() const { return (ImmutableOopMapPair*) ((address) this + sizeof(*this)); }
+
+  static ImmutableOopMapSet* build_from(const OopMapSet* oopmap_set);
+
+  const ImmutableOopMap* find_map_at_offset(int pc_offset) const;
+
+  const ImmutableOopMapPair* pair_at(int index) const { assert(index >= 0 && index < _count, "check"); return &get_pairs()[index]; }
+
+  int count() const { return _count; }
+  int nr_of_bytes() const { return _size; }
+
+  void print_on(outputStream* st) const;
+  void print() const { print_on(tty); }
+};
 
 class OopMapStream : public StackObj {
  private:
@@ -273,8 +341,8 @@
   void find_next();
 
  public:
-  OopMapStream(OopMap* oop_map);
-  OopMapStream(OopMap* oop_map, int oop_types_mask);
+  OopMapStream(OopMap* oop_map, int oop_types_mask = OopMapValue::type_mask_in_place);
+  OopMapStream(const ImmutableOopMap* oop_map, int oop_types_mask = OopMapValue::type_mask_in_place);
   bool is_done()                        { if(!_valid_omv) { find_next(); } return !_valid_omv; }
   void next()                           { find_next(); }
   OopMapValue current()                 { return _omv; }
--- a/hotspot/src/share/vm/gc_implementation/concurrentMarkSweep/adaptiveFreeList.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/concurrentMarkSweep/adaptiveFreeList.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2001, 2013, 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,8 +22,8 @@
  *
  */
 
-#ifndef SHARE_VM_MEMORY_ADAPTIVEFREELIST_HPP
-#define SHARE_VM_MEMORY_ADAPTIVEFREELIST_HPP
+#ifndef SHARE_VM_GC_IMPLEMENTATION_CONCURRENTMARKSWEEP_ADAPTIVEFREELIST_HPP
+#define SHARE_VM_GC_IMPLEMENTATION_CONCURRENTMARKSWEEP_ADAPTIVEFREELIST_HPP
 
 #include "memory/freeList.hpp"
 #include "gc_implementation/shared/allocationStats.hpp"
@@ -226,4 +226,4 @@
 #endif  // NOT PRODUCT
 };
 
-#endif // SHARE_VM_MEMORY_ADAPTIVEFREELIST_HPP
+#endif // SHARE_VM_GC_IMPLEMENTATION_CONCURRENTMARKSWEEP_ADAPTIVEFREELIST_HPP
--- a/hotspot/src/share/vm/gc_implementation/concurrentMarkSweep/cmsOopClosures.inline.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/concurrentMarkSweep/cmsOopClosures.inline.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -28,6 +28,7 @@
 #include "gc_implementation/concurrentMarkSweep/cmsOopClosures.hpp"
 #include "gc_implementation/concurrentMarkSweep/concurrentMarkSweepGeneration.hpp"
 #include "oops/oop.inline.hpp"
+#include "utilities/taskqueue.inline.hpp"
 
 // Trim our work_queue so its length is below max at return
 inline void Par_MarkRefsIntoAndScanClosure::trim_queue(uint max) {
--- a/hotspot/src/share/vm/gc_implementation/concurrentMarkSweep/compactibleFreeListSpace.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/concurrentMarkSweep/compactibleFreeListSpace.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1082,17 +1082,6 @@
 bool CompactibleFreeListSpace::block_is_obj(const HeapWord* p) const {
   FreeChunk* fc = (FreeChunk*)p;
   assert(is_in_reserved(p), "Should be in space");
-  // When doing a mark-sweep-compact of the CMS generation, this
-  // assertion may fail because prepare_for_compaction() uses
-  // space that is garbage to maintain information on ranges of
-  // live objects so that these live ranges can be moved as a whole.
-  // Comment out this assertion until that problem can be solved
-  // (i.e., that the block start calculation may look at objects
-  // at address below "p" in finding the object that contains "p"
-  // and those objects (if garbage) may have been modified to hold
-  // live range information.
-  // assert(CollectedHeap::use_parallel_gc_threads() || _bt.block_start(p) == p,
-  //        "Should be a block boundary");
   if (FreeChunk::indicatesFreeChunk(p)) return false;
   Klass* k = oop(p)->klass_or_null();
   if (k != NULL) {
--- a/hotspot/src/share/vm/gc_implementation/concurrentMarkSweep/concurrentMarkSweepGeneration.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/concurrentMarkSweep/concurrentMarkSweepGeneration.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -66,6 +66,7 @@
 #include "services/memoryService.hpp"
 #include "services/runtimeService.hpp"
 #include "utilities/stack.inline.hpp"
+#include "utilities/taskqueue.inline.hpp"
 
 // statics
 CMSCollector* ConcurrentMarkSweepGeneration::_collector = NULL;
@@ -224,16 +225,12 @@
            "Offset of FreeChunk::_prev within FreeChunk must match"
            "  that of OopDesc::_klass within OopDesc");
   )
-  if (CollectedHeap::use_parallel_gc_threads()) {
-    typedef CMSParGCThreadState* CMSParGCThreadStatePtr;
-    _par_gc_thread_states =
-      NEW_C_HEAP_ARRAY(CMSParGCThreadStatePtr, ParallelGCThreads, mtGC);
-    for (uint i = 0; i < ParallelGCThreads; i++) {
-      _par_gc_thread_states[i] = new CMSParGCThreadState(cmsSpace());
-    }
-  } else {
-    _par_gc_thread_states = NULL;
-  }
+
+  _par_gc_thread_states = NEW_C_HEAP_ARRAY(CMSParGCThreadState*, ParallelGCThreads, mtGC);
+  for (uint i = 0; i < ParallelGCThreads; i++) {
+    _par_gc_thread_states[i] = new CMSParGCThreadState(cmsSpace());
+  }
+
   _incremental_collection_failed = false;
   // The "dilatation_factor" is the expansion that can occur on
   // account of the fact that the minimum object size in the CMS
@@ -459,7 +456,6 @@
   _markBitMap(0, Mutex::leaf + 1, "CMS_markBitMap_lock"),
   _modUnionTable((CardTableModRefBS::card_shift - LogHeapWordSize),
                  -1 /* lock-free */, "No_lock" /* dummy */),
-  _modUnionClosure(&_modUnionTable),
   _modUnionClosurePar(&_modUnionTable),
   // Adjust my span to cover old (cms) gen
   _span(cmsGen->reserved()),
@@ -2129,10 +2125,7 @@
 
   bool registerClosure = duringMarking;
 
-  ModUnionClosure* muc = CollectedHeap::use_parallel_gc_threads() ?
-                                               &_modUnionClosurePar
-                                               : &_modUnionClosure;
-  _cmsGen->gc_prologue_work(full, registerClosure, muc);
+  _cmsGen->gc_prologue_work(full, registerClosure, &_modUnionClosurePar);
 
   if (!full) {
     stats().record_gc0_begin();
@@ -2905,8 +2898,8 @@
 class CMSParMarkTask : public AbstractGangTask {
  protected:
   CMSCollector*     _collector;
-  int               _n_workers;
-  CMSParMarkTask(const char* name, CMSCollector* collector, int n_workers) :
+  uint              _n_workers;
+  CMSParMarkTask(const char* name, CMSCollector* collector, uint n_workers) :
       AbstractGangTask(name),
       _collector(collector),
       _n_workers(n_workers) {}
@@ -2920,7 +2913,7 @@
 // Parallel initial mark task
 class CMSParInitialMarkTask: public CMSParMarkTask {
  public:
-  CMSParInitialMarkTask(CMSCollector* collector, int n_workers) :
+  CMSParInitialMarkTask(CMSCollector* collector, uint n_workers) :
       CMSParMarkTask("Scan roots and young gen for initial mark in parallel",
                      collector, n_workers) {}
   void work(uint worker_id);
@@ -3005,11 +2998,11 @@
 
   {
     COMPILER2_PRESENT(DerivedPointerTableDeactivate dpt_deact;)
-    if (CMSParallelInitialMarkEnabled && CollectedHeap::use_parallel_gc_threads()) {
+    if (CMSParallelInitialMarkEnabled) {
       // The parallel version.
       FlexibleWorkGang* workers = gch->workers();
       assert(workers != NULL, "Need parallel worker threads.");
-      int n_workers = workers->active_workers();
+      uint n_workers = workers->active_workers();
       CMSParInitialMarkTask tsk(this, n_workers);
       gch->set_par_threads(n_workers);
       initialize_sequential_subtasks_for_young_gen_rescan(n_workers);
@@ -3150,7 +3143,7 @@
 // MT Concurrent Marking Task
 class CMSConcMarkingTask: public YieldingFlexibleGangTask {
   CMSCollector* _collector;
-  int           _n_workers;                  // requested/desired # workers
+  uint          _n_workers;       // requested/desired # workers
   bool          _result;
   CompactibleFreeListSpace*  _cms_space;
   char          _pad_front[64];   // padding to ...
@@ -3196,7 +3189,7 @@
 
   CMSConcMarkingTerminator* terminator() { return &_term; }
 
-  virtual void set_for_termination(int active_workers) {
+  virtual void set_for_termination(uint active_workers) {
     terminator()->reset_for_reuse(active_workers);
   }
 
@@ -3642,10 +3635,9 @@
 
 bool CMSCollector::do_marking_mt() {
   assert(ConcGCThreads > 0 && conc_workers() != NULL, "precondition");
-  int num_workers = AdaptiveSizePolicy::calc_active_conc_workers(
-                                       conc_workers()->total_workers(),
-                                       conc_workers()->active_workers(),
-                                       Threads::number_of_non_daemon_threads());
+  uint num_workers = AdaptiveSizePolicy::calc_active_conc_workers(conc_workers()->total_workers(),
+                                                                  conc_workers()->active_workers(),
+                                                                  Threads::number_of_non_daemon_threads());
   conc_workers()->set_active_workers(num_workers);
 
   CompactibleFreeListSpace* cms_space  = _cmsGen->cmsSpace();
@@ -4347,7 +4339,7 @@
     // dirtied since the first checkpoint in this GC cycle and prior to
     // the most recent young generation GC, minus those cleaned up by the
     // concurrent precleaning.
-    if (CMSParallelRemarkEnabled && CollectedHeap::use_parallel_gc_threads()) {
+    if (CMSParallelRemarkEnabled) {
       GCTraceTime t("Rescan (parallel) ", PrintGCDetails, false, _gc_timer_cm, _gc_tracer_cm->gc_id());
       do_remark_parallel();
     } else {
@@ -4491,7 +4483,7 @@
   // workers to be taken from the active workers in the work gang.
   CMSParRemarkTask(CMSCollector* collector,
                    CompactibleFreeListSpace* cms_space,
-                   int n_workers, FlexibleWorkGang* workers,
+                   uint n_workers, FlexibleWorkGang* workers,
                    OopTaskQueueSet* task_queues):
     CMSParMarkTask("Rescan roots and grey objects in parallel",
                    collector, n_workers),
@@ -4504,7 +4496,7 @@
   OopTaskQueue* work_queue(int i) { return task_queues()->queue(i); }
 
   ParallelTaskTerminator* terminator() { return &_term; }
-  int n_workers() { return _n_workers; }
+  uint n_workers() { return _n_workers; }
 
   void work(uint worker_id);
 
@@ -5067,7 +5059,7 @@
   // Choose to use the number of GC workers most recently set
   // into "active_workers".  If active_workers is not set, set it
   // to ParallelGCThreads.
-  int n_workers = workers->active_workers();
+  uint n_workers = workers->active_workers();
   if (n_workers == 0) {
     assert(n_workers > 0, "Should have been set during scavenge");
     n_workers = ParallelGCThreads;
@@ -5433,7 +5425,7 @@
       // That is OK as long as the Reference lists are balanced (see
       // balance_all_queues() and balance_queues()).
       GenCollectedHeap* gch = GenCollectedHeap::heap();
-      int active_workers = ParallelGCThreads;
+      uint active_workers = ParallelGCThreads;
       FlexibleWorkGang* workers = gch->workers();
       if (workers != NULL) {
         active_workers = workers->active_workers();
--- a/hotspot/src/share/vm/gc_implementation/concurrentMarkSweep/concurrentMarkSweepGeneration.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/concurrentMarkSweep/concurrentMarkSweepGeneration.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -647,7 +647,6 @@
   // Keep this textually after _markBitMap and _span; c'tor dependency.
 
   ConcurrentMarkSweepThread*     _cmsThread;   // The thread doing the work
-  ModUnionClosure    _modUnionClosure;
   ModUnionClosurePar _modUnionClosurePar;
 
   // CMS abstract state machine
--- a/hotspot/src/share/vm/gc_implementation/g1/concurrentG1RefineThread.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/concurrentG1RefineThread.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2001, 2014, 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
@@ -77,7 +77,7 @@
 }
 
 void ConcurrentG1RefineThread::sample_young_list_rs_lengths() {
-  SuspendibleThreadSetJoiner sts;
+  SuspendibleThreadSetJoiner sts_join;
   G1CollectedHeap* g1h = G1CollectedHeap::heap();
   G1CollectorPolicy* g1p = g1h->g1_policy();
   if (g1p->adaptive_young_list_length()) {
@@ -89,8 +89,8 @@
 
       // we try to yield every time we visit 10 regions
       if (regions_visited == 10) {
-        if (sts.should_yield()) {
-          sts.yield();
+        if (sts_join.should_yield()) {
+          sts_join.yield();
           // we just abandon the iteration
           break;
         }
@@ -188,7 +188,7 @@
     }
 
     {
-      SuspendibleThreadSetJoiner sts;
+      SuspendibleThreadSetJoiner sts_join;
 
       do {
         int curr_buffer_num = (int)dcqs.completed_buffers_num();
--- a/hotspot/src/share/vm/gc_implementation/g1/concurrentMark.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/concurrentMark.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -54,6 +54,7 @@
 #include "runtime/atomic.inline.hpp"
 #include "runtime/prefetch.inline.hpp"
 #include "services/memTracker.hpp"
+#include "utilities/taskqueue.inline.hpp"
 
 // Concurrent marking bit map wrapper
 
@@ -192,13 +193,8 @@
       _cl(cl), _suspendible(suspendible), AbstractGangTask("Parallel Clear Bitmap Task"), _hrclaimer(n_workers) {}
 
   void work(uint worker_id) {
-    if (_suspendible) {
-      SuspendibleThreadSet::join();
-    }
+    SuspendibleThreadSetJoiner sts_join(_suspendible);
     G1CollectedHeap::heap()->heap_region_par_iterate(_cl, worker_id, &_hrclaimer, true);
-    if (_suspendible) {
-      SuspendibleThreadSet::leave();
-    }
   }
 };
 
@@ -274,7 +270,6 @@
   _capacity = (jint) capacity;
   _saved_index = -1;
   _should_expand = false;
-  NOT_PRODUCT(_max_depth = 0);
   return true;
 }
 
@@ -330,54 +325,6 @@
   }
 }
 
-void CMMarkStack::par_push(oop ptr) {
-  while (true) {
-    if (isFull()) {
-      _overflow = true;
-      return;
-    }
-    // Otherwise...
-    jint index = _index;
-    jint next_index = index+1;
-    jint res = Atomic::cmpxchg(next_index, &_index, index);
-    if (res == index) {
-      _base[index] = ptr;
-      // Note that we don't maintain this atomically.  We could, but it
-      // doesn't seem necessary.
-      NOT_PRODUCT(_max_depth = MAX2(_max_depth, next_index));
-      return;
-    }
-    // Otherwise, we need to try again.
-  }
-}
-
-void CMMarkStack::par_adjoin_arr(oop* ptr_arr, int n) {
-  while (true) {
-    if (isFull()) {
-      _overflow = true;
-      return;
-    }
-    // Otherwise...
-    jint index = _index;
-    jint next_index = index + n;
-    if (next_index > _capacity) {
-      _overflow = true;
-      return;
-    }
-    jint res = Atomic::cmpxchg(next_index, &_index, index);
-    if (res == index) {
-      for (int i = 0; i < n; i++) {
-        int  ind = index + i;
-        assert(ind < _capacity, "By overflow test above.");
-        _base[ind] = ptr_arr[i];
-      }
-      NOT_PRODUCT(_max_depth = MAX2(_max_depth, next_index));
-      return;
-    }
-    // Otherwise, we need to try again.
-  }
-}
-
 void CMMarkStack::par_push_arr(oop* ptr_arr, int n) {
   MutexLockerEx x(ParGCRareEvent_lock, Mutex::_no_safepoint_check_flag);
   jint start = _index;
@@ -393,7 +340,6 @@
     assert(ind < _capacity, "By overflow test above.");
     _base[ind] = ptr_arr[i];
   }
-  NOT_PRODUCT(_max_depth = MAX2(_max_depth, next_index));
 }
 
 bool CMMarkStack::par_pop_arr(oop* ptr_arr, int max, int* n) {
@@ -1005,19 +951,17 @@
  */
 
 void ConcurrentMark::enter_first_sync_barrier(uint worker_id) {
+  bool barrier_aborted;
+
   if (verbose_low()) {
     gclog_or_tty->print_cr("[%u] entering first barrier", worker_id);
   }
 
-  if (concurrent()) {
-    SuspendibleThreadSet::leave();
+  {
+    SuspendibleThreadSetLeaver sts_leave(concurrent());
+    barrier_aborted = !_first_overflow_barrier_sync.enter();
   }
 
-  bool barrier_aborted = !_first_overflow_barrier_sync.enter();
-
-  if (concurrent()) {
-    SuspendibleThreadSet::join();
-  }
   // at this point everyone should have synced up and not be doing any
   // more work
 
@@ -1064,19 +1008,17 @@
 }
 
 void ConcurrentMark::enter_second_sync_barrier(uint worker_id) {
+  bool barrier_aborted;
+
   if (verbose_low()) {
     gclog_or_tty->print_cr("[%u] entering second barrier", worker_id);
   }
 
-  if (concurrent()) {
-    SuspendibleThreadSet::leave();
+  {
+    SuspendibleThreadSetLeaver sts_leave(concurrent());
+    barrier_aborted = !_second_overflow_barrier_sync.enter();
   }
 
-  bool barrier_aborted = !_second_overflow_barrier_sync.enter();
-
-  if (concurrent()) {
-    SuspendibleThreadSet::join();
-  }
   // at this point everything should be re-initialized and ready to go
 
   if (verbose_low()) {
@@ -1127,40 +1069,41 @@
 
     double start_vtime = os::elapsedVTime();
 
-    SuspendibleThreadSet::join();
-
-    assert(worker_id < _cm->active_tasks(), "invariant");
-    CMTask* the_task = _cm->task(worker_id);
-    the_task->record_start_time();
-    if (!_cm->has_aborted()) {
-      do {
-        double start_vtime_sec = os::elapsedVTime();
-        double mark_step_duration_ms = G1ConcMarkStepDurationMillis;
-
-        the_task->do_marking_step(mark_step_duration_ms,
-                                  true  /* do_termination */,
-                                  false /* is_serial*/);
-
-        double end_vtime_sec = os::elapsedVTime();
-        double elapsed_vtime_sec = end_vtime_sec - start_vtime_sec;
-        _cm->clear_has_overflown();
-
-        _cm->do_yield_check(worker_id);
-
-        jlong sleep_time_ms;
-        if (!_cm->has_aborted() && the_task->has_aborted()) {
-          sleep_time_ms =
-            (jlong) (elapsed_vtime_sec * _cm->sleep_factor() * 1000.0);
-          SuspendibleThreadSet::leave();
-          os::sleep(Thread::current(), sleep_time_ms, false);
-          SuspendibleThreadSet::join();
-        }
-      } while (!_cm->has_aborted() && the_task->has_aborted());
+    {
+      SuspendibleThreadSetJoiner sts_join;
+
+      assert(worker_id < _cm->active_tasks(), "invariant");
+      CMTask* the_task = _cm->task(worker_id);
+      the_task->record_start_time();
+      if (!_cm->has_aborted()) {
+        do {
+          double start_vtime_sec = os::elapsedVTime();
+          double mark_step_duration_ms = G1ConcMarkStepDurationMillis;
+
+          the_task->do_marking_step(mark_step_duration_ms,
+                                    true  /* do_termination */,
+                                    false /* is_serial*/);
+
+          double end_vtime_sec = os::elapsedVTime();
+          double elapsed_vtime_sec = end_vtime_sec - start_vtime_sec;
+          _cm->clear_has_overflown();
+
+          _cm->do_yield_check(worker_id);
+
+          jlong sleep_time_ms;
+          if (!_cm->has_aborted() && the_task->has_aborted()) {
+            sleep_time_ms =
+              (jlong) (elapsed_vtime_sec * _cm->sleep_factor() * 1000.0);
+            {
+              SuspendibleThreadSetLeaver sts_leave;
+              os::sleep(Thread::current(), sleep_time_ms, false);
+            }
+          }
+        } while (!_cm->has_aborted() && the_task->has_aborted());
+      }
+      the_task->record_end_time();
+      guarantee(!the_task->has_aborted() || _cm->has_aborted(), "invariant");
     }
-    the_task->record_end_time();
-    guarantee(!the_task->has_aborted() || _cm->has_aborted(), "invariant");
-
-    SuspendibleThreadSet::leave();
 
     double end_vtime = os::elapsedVTime();
     _cm->update_accum_task_vtime(worker_id, end_vtime - start_vtime);
@@ -2314,13 +2257,13 @@
   G1CollectedHeap* _g1h;
   ConcurrentMark*  _cm;
   WorkGang*        _workers;
-  int              _active_workers;
+  uint             _active_workers;
 
 public:
   G1CMRefProcTaskExecutor(G1CollectedHeap* g1h,
-                        ConcurrentMark* cm,
-                        WorkGang* workers,
-                        int n_workers) :
+                          ConcurrentMark* cm,
+                          WorkGang* workers,
+                          uint n_workers) :
     _g1h(g1h), _cm(cm),
     _workers(workers), _active_workers(n_workers) { }
 
@@ -2551,31 +2494,50 @@
   _nextMarkBitMap  = (CMBitMap*)  temp;
 }
 
-class CMObjectClosure;
-
-// Closure for iterating over objects, currently only used for
-// processing SATB buffers.
-class CMObjectClosure : public ObjectClosure {
+// Closure for marking entries in SATB buffers.
+class CMSATBBufferClosure : public SATBBufferClosure {
 private:
   CMTask* _task;
+  G1CollectedHeap* _g1h;
+
+  // This is very similar to CMTask::deal_with_reference, but with
+  // more relaxed requirements for the argument, so this must be more
+  // circumspect about treating the argument as an object.
+  void do_entry(void* entry) const {
+    _task->increment_refs_reached();
+    HeapRegion* hr = _g1h->heap_region_containing_raw(entry);
+    if (entry < hr->next_top_at_mark_start()) {
+      // Until we get here, we don't know whether entry refers to a valid
+      // object; it could instead have been a stale reference.
+      oop obj = static_cast<oop>(entry);
+      assert(obj->is_oop(true /* ignore mark word */),
+             err_msg("Invalid oop in SATB buffer: " PTR_FORMAT, p2i(obj)));
+      _task->make_reference_grey(obj, hr);
+    }
+  }
 
 public:
-  void do_object(oop obj) {
-    _task->deal_with_reference(obj);
+  CMSATBBufferClosure(CMTask* task, G1CollectedHeap* g1h)
+    : _task(task), _g1h(g1h) { }
+
+  virtual void do_buffer(void** buffer, size_t size) {
+    for (size_t i = 0; i < size; ++i) {
+      do_entry(buffer[i]);
+    }
   }
-
-  CMObjectClosure(CMTask* task) : _task(task) { }
 };
 
 class G1RemarkThreadsClosure : public ThreadClosure {
-  CMObjectClosure _cm_obj;
+  CMSATBBufferClosure _cm_satb_cl;
   G1CMOopClosure _cm_cl;
   MarkingCodeBlobClosure _code_cl;
   int _thread_parity;
 
  public:
   G1RemarkThreadsClosure(G1CollectedHeap* g1h, CMTask* task) :
-    _cm_obj(task), _cm_cl(g1h, g1h->concurrent_mark(), task), _code_cl(&_cm_cl, !CodeBlobToOopClosure::FixRelocations),
+    _cm_satb_cl(task, g1h),
+    _cm_cl(g1h, g1h->concurrent_mark(), task),
+    _code_cl(&_cm_cl, !CodeBlobToOopClosure::FixRelocations),
     _thread_parity(Threads::thread_claim_parity()) {}
 
   void do_thread(Thread* thread) {
@@ -2591,11 +2553,11 @@
         // live by the SATB invariant but other oops recorded in nmethods may behave differently.
         jt->nmethods_do(&_code_cl);
 
-        jt->satb_mark_queue().apply_closure_and_empty(&_cm_obj);
+        jt->satb_mark_queue().apply_closure_and_empty(&_cm_satb_cl);
       }
     } else if (thread->is_VM_thread()) {
       if (thread->claim_oops_do(true, _thread_parity)) {
-        JavaThread::satb_mark_queue_set().shared_satb_queue()->apply_closure_and_empty(&_cm_obj);
+        JavaThread::satb_mark_queue_set().shared_satb_queue()->apply_closure_and_empty(&_cm_satb_cl);
       }
     }
   }
@@ -2630,7 +2592,7 @@
     }
   }
 
-  CMRemarkTask(ConcurrentMark* cm, int active_workers) :
+  CMRemarkTask(ConcurrentMark* cm, uint active_workers) :
     AbstractGangTask("Par Remark"), _cm(cm) {
     _cm->terminator()->reset_for_reuse(active_workers);
   }
@@ -3008,7 +2970,7 @@
   ConcurrentMark* _cm;
   BitMap* _cm_card_bm;
   uint _max_worker_id;
-  int _active_workers;
+  uint _active_workers;
   HeapRegionClaimer _hrclaimer;
 
 public:
@@ -3016,7 +2978,7 @@
                            ConcurrentMark* cm,
                            BitMap* cm_card_bm,
                            uint max_worker_id,
-                           int n_workers) :
+                           uint n_workers) :
       AbstractGangTask("Count Aggregation"),
       _g1h(g1h), _cm(cm), _cm_card_bm(cm_card_bm),
       _max_worker_id(max_worker_id),
@@ -3033,7 +2995,7 @@
 
 
 void ConcurrentMark::aggregate_count_data() {
-  int n_workers = _g1h->workers()->active_workers();
+  uint n_workers = _g1h->workers()->active_workers();
 
   G1AggregateCountDataTask g1_par_agg_task(_g1h, this, &_card_bm,
                                            _max_worker_id, n_workers);
@@ -3693,13 +3655,13 @@
   // very counter productive if it did that. :-)
   _draining_satb_buffers = true;
 
-  CMObjectClosure oc(this);
+  CMSATBBufferClosure satb_cl(this, _g1h);
   SATBMarkQueueSet& satb_mq_set = JavaThread::satb_mark_queue_set();
 
   // This keeps claiming and applying the closure to completed buffers
   // until we run out of buffers or we need to abort.
   while (!has_aborted() &&
-         satb_mq_set.apply_closure_to_completed_buffer(&oc)) {
+         satb_mq_set.apply_closure_to_completed_buffer(&satb_cl)) {
     if (_cm->verbose_medium()) {
       gclog_or_tty->print_cr("[%u] processed an SATB buffer", _worker_id);
     }
@@ -3758,6 +3720,10 @@
 #endif // _MARKING_STATS_
 }
 
+bool ConcurrentMark::try_stealing(uint worker_id, int* hash_seed, oop& obj) {
+  return _task_queues->steal(worker_id, hash_seed, obj);
+}
+
 /*****************************************************************************
 
     The do_marking_step(time_target_ms, ...) method is the building
--- a/hotspot/src/share/vm/gc_implementation/g1/concurrentMark.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/concurrentMark.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -139,6 +139,11 @@
   static size_t compute_size(size_t heap_size);
   // Returns the amount of bytes on the heap between two marks in the bitmap.
   static size_t mark_distance();
+  // Returns how many bytes (or bits) of the heap a single byte (or bit) of the
+  // mark bitmap corresponds to. This is the same as the mark distance above.
+  static size_t heap_map_factor() {
+    return mark_distance();
+  }
 
   CMBitMap() : CMBitMapRO(LogMinObjAlignment), _listener() { _listener.set_bitmap(this); }
 
@@ -175,25 +180,12 @@
   jint _index;       // one more than last occupied index
   jint _capacity;    // max #elements
   jint _saved_index; // value of _index saved at start of GC
-  NOT_PRODUCT(jint _max_depth;)   // max depth plumbed during run
 
   bool  _overflow;
   bool  _should_expand;
   DEBUG_ONLY(bool _drain_in_progress;)
   DEBUG_ONLY(bool _drain_in_progress_yields;)
 
- public:
-  CMMarkStack(ConcurrentMark* cm);
-  ~CMMarkStack();
-
-#ifndef PRODUCT
-  jint max_depth() const {
-    return _max_depth;
-  }
-#endif
-
-  bool allocate(size_t capacity);
-
   oop pop() {
     if (!isEmpty()) {
       return _base[--_index] ;
@@ -201,27 +193,11 @@
     return NULL;
   }
 
-  // If overflow happens, don't do the push, and record the overflow.
-  // *Requires* that "ptr" is already marked.
-  void push(oop ptr) {
-    if (isFull()) {
-      // Record overflow.
-      _overflow = true;
-      return;
-    } else {
-      _base[_index++] = ptr;
-      NOT_PRODUCT(_max_depth = MAX2(_max_depth, _index));
-    }
-  }
-  // Non-block impl.  Note: concurrency is allowed only with other
-  // "par_push" operations, not with "pop" or "drain".  We would need
-  // parallel versions of them if such concurrency was desired.
-  void par_push(oop ptr);
+ public:
+  CMMarkStack(ConcurrentMark* cm);
+  ~CMMarkStack();
 
-  // Pushes the first "n" elements of "ptr_arr" on the stack.
-  // Non-block impl.  Note: concurrency is allowed only with other
-  // "par_adjoin_arr" or "push" operations, not with "pop" or "drain".
-  void par_adjoin_arr(oop* ptr_arr, int n);
+  bool allocate(size_t capacity);
 
   // Pushes the first "n" elements of "ptr_arr" on the stack.
   // Locking impl: concurrency is allowed only with
@@ -249,7 +225,6 @@
   bool drain(OopClosureClass* cl, CMBitMap* bm, bool yield_after = false);
 
   bool isEmpty()    { return _index == 0; }
-  bool isFull()     { return _index == _capacity; }
   int  maxElems()   { return _capacity; }
 
   bool overflow() { return _overflow; }
@@ -373,7 +348,6 @@
   friend class ConcurrentMarkThread;
   friend class CMTask;
   friend class CMBitMapClosure;
-  friend class CMGlobalObjectClosure;
   friend class CMRemarkTask;
   friend class CMConcurrentMarkingTask;
   friend class G1ParNoteEndTask;
@@ -468,8 +442,8 @@
   // All of these times are in ms
   NumberSeq _init_times;
   NumberSeq _remark_times;
-  NumberSeq   _remark_mark_times;
-  NumberSeq   _remark_weak_ref_times;
+  NumberSeq _remark_mark_times;
+  NumberSeq _remark_weak_ref_times;
   NumberSeq _cleanup_times;
   double    _total_counting_time;
   double    _total_rs_scrub_time;
@@ -618,19 +592,9 @@
 
 public:
   // Manipulation of the global mark stack.
-  // Notice that the first mark_stack_push is CAS-based, whereas the
-  // two below are Mutex-based. This is OK since the first one is only
-  // called during evacuation pauses and doesn't compete with the
-  // other two (which are called by the marking tasks during
-  // concurrent marking or remark).
-  bool mark_stack_push(oop p) {
-    _markStack.par_push(p);
-    if (_markStack.overflow()) {
-      set_has_overflown();
-      return false;
-    }
-    return true;
-  }
+  // The push and pop operations are used by tasks for transfers
+  // between task-local queues and the global mark stack, and use
+  // locking for concurrency safety.
   bool mark_stack_push(oop* arr, int n) {
     _markStack.par_push_arr(arr, n);
     if (_markStack.overflow()) {
@@ -671,9 +635,7 @@
   }
 
   // Attempts to steal an object from the task queues of other tasks
-  bool try_stealing(uint worker_id, int* hash_seed, oop& obj) {
-    return _task_queues->steal(worker_id, hash_seed, obj);
-  }
+  bool try_stealing(uint worker_id, int* hash_seed, oop& obj);
 
   ConcurrentMark(G1CollectedHeap* g1h,
                  G1RegionToSpaceMapper* prev_bitmap_storage,
@@ -1095,9 +1057,9 @@
   void regular_clock_call();
   bool concurrent() { return _concurrent; }
 
-  // Test whether objAddr might have already been passed over by the
+  // Test whether obj might have already been passed over by the
   // mark bitmap scan, and so needs to be pushed onto the mark stack.
-  bool is_below_finger(HeapWord* objAddr, HeapWord* global_finger) const;
+  bool is_below_finger(oop obj, HeapWord* global_finger) const;
 
   template<bool scan> void process_grey_object(oop obj);
 
@@ -1148,8 +1110,18 @@
 
   void set_cm_oop_closure(G1CMOopClosure* cm_oop_closure);
 
-  // It grays the object by marking it and, if necessary, pushing it
-  // on the local queue
+  // Increment the number of references this task has visited.
+  void increment_refs_reached() { ++_refs_reached; }
+
+  // Grey the object by marking it.  If not already marked, push it on
+  // the local queue if below the finger.
+  // Precondition: obj is in region.
+  // Precondition: obj is below region's NTAMS.
+  inline void make_reference_grey(oop obj, HeapRegion* region);
+
+  // Grey the object (by calling make_grey_reference) if required,
+  // e.g. obj is below its containing region's NTAMS.
+  // Precondition: obj is a valid heap object.
   inline void deal_with_reference(oop obj);
 
   // It scans an object and visits its children.
--- a/hotspot/src/share/vm/gc_implementation/g1/concurrentMark.inline.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/concurrentMark.inline.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -27,6 +27,7 @@
 
 #include "gc_implementation/g1/concurrentMark.hpp"
 #include "gc_implementation/g1/g1CollectedHeap.inline.hpp"
+#include "utilities/taskqueue.inline.hpp"
 
 // Utility routine to set an exclusive range of cards on the given
 // card liveness bitmap
@@ -259,15 +260,15 @@
              ++_local_pushes );
 }
 
-inline bool CMTask::is_below_finger(HeapWord* objAddr,
-                                    HeapWord* global_finger) const {
-  // If objAddr is above the global finger, then the mark bitmap scan
+inline bool CMTask::is_below_finger(oop obj, HeapWord* global_finger) const {
+  // If obj is above the global finger, then the mark bitmap scan
   // will find it later, and no push is needed.  Similarly, if we have
-  // a current region and objAddr is between the local finger and the
+  // a current region and obj is between the local finger and the
   // end of the current region, then no push is needed.  The tradeoff
   // of checking both vs only checking the global finger is that the
   // local check will be more accurate and so result in fewer pushes,
   // but may also be a little slower.
+  HeapWord* objAddr = (HeapWord*)obj;
   if (_finger != NULL) {
     // We have a current region.
 
@@ -277,7 +278,7 @@
     assert(_region_limit != NULL, "invariant");
     assert(_region_limit <= global_finger, "invariant");
 
-    // True if objAddr is less than the local finger, or is between
+    // True if obj is less than the local finger, or is between
     // the region limit and the global finger.
     if (objAddr < _finger) {
       return true;
@@ -289,13 +290,65 @@
   return objAddr < global_finger;
 }
 
+inline void CMTask::make_reference_grey(oop obj, HeapRegion* hr) {
+  if (_cm->par_mark_and_count(obj, hr, _marked_bytes_array, _card_bm)) {
+
+    if (_cm->verbose_high()) {
+      gclog_or_tty->print_cr("[%u] marked object " PTR_FORMAT,
+                             _worker_id, p2i(obj));
+    }
+
+    // No OrderAccess:store_load() is needed. It is implicit in the
+    // CAS done in CMBitMap::parMark() call in the routine above.
+    HeapWord* global_finger = _cm->finger();
+
+    // We only need to push a newly grey object on the mark
+    // stack if it is in a section of memory the mark bitmap
+    // scan has already examined.  Mark bitmap scanning
+    // maintains progress "fingers" for determining that.
+    //
+    // Notice that the global finger might be moving forward
+    // concurrently. This is not a problem. In the worst case, we
+    // mark the object while it is above the global finger and, by
+    // the time we read the global finger, it has moved forward
+    // past this object. In this case, the object will probably
+    // be visited when a task is scanning the region and will also
+    // be pushed on the stack. So, some duplicate work, but no
+    // correctness problems.
+    if (is_below_finger(obj, global_finger)) {
+      if (obj->is_typeArray()) {
+        // Immediately process arrays of primitive types, rather
+        // than pushing on the mark stack.  This keeps us from
+        // adding humongous objects to the mark stack that might
+        // be reclaimed before the entry is processed - see
+        // selection of candidates for eager reclaim of humongous
+        // objects.  The cost of the additional type test is
+        // mitigated by avoiding a trip through the mark stack,
+        // by only doing a bookkeeping update and avoiding the
+        // actual scan of the object - a typeArray contains no
+        // references, and the metadata is built-in.
+        process_grey_object<false>(obj);
+      } else {
+        if (_cm->verbose_high()) {
+          gclog_or_tty->print_cr("[%u] below a finger (local: " PTR_FORMAT
+                                 ", global: " PTR_FORMAT ") pushing "
+                                 PTR_FORMAT " on mark stack",
+                                 _worker_id, p2i(_finger),
+                                 p2i(global_finger), p2i(obj));
+        }
+        push(obj);
+      }
+    }
+  }
+}
+
 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,
                            _worker_id, p2i((void*) obj));
   }
 
-  ++_refs_reached;
+  increment_refs_reached();
 
   HeapWord* objAddr = (HeapWord*) obj;
   assert(obj->is_oop_or_null(true /* ignore mark word */), err_msg("Expected an oop or NULL at " PTR_FORMAT, p2i(obj)));
@@ -307,55 +360,7 @@
       // anything with it).
       HeapRegion* hr = _g1h->heap_region_containing_raw(obj);
       if (!hr->obj_allocated_since_next_marking(obj)) {
-        if (_cm->verbose_high()) {
-          gclog_or_tty->print_cr("[%u] "PTR_FORMAT" is not considered marked",
-                                 _worker_id, p2i((void*) obj));
-        }
-
-        // we need to mark it first
-        if (_cm->par_mark_and_count(obj, hr, _marked_bytes_array, _card_bm)) {
-          // No OrderAccess:store_load() is needed. It is implicit in the
-          // CAS done in CMBitMap::parMark() call in the routine above.
-          HeapWord* global_finger = _cm->finger();
-
-          // We only need to push a newly grey object on the mark
-          // stack if it is in a section of memory the mark bitmap
-          // scan has already examined.  Mark bitmap scanning
-          // maintains progress "fingers" for determining that.
-          //
-          // Notice that the global finger might be moving forward
-          // concurrently. This is not a problem. In the worst case, we
-          // mark the object while it is above the global finger and, by
-          // the time we read the global finger, it has moved forward
-          // past this object. In this case, the object will probably
-          // be visited when a task is scanning the region and will also
-          // be pushed on the stack. So, some duplicate work, but no
-          // correctness problems.
-          if (is_below_finger(objAddr, global_finger)) {
-            if (obj->is_typeArray()) {
-              // Immediately process arrays of primitive types, rather
-              // than pushing on the mark stack.  This keeps us from
-              // adding humongous objects to the mark stack that might
-              // be reclaimed before the entry is processed - see
-              // selection of candidates for eager reclaim of humongous
-              // objects.  The cost of the additional type test is
-              // mitigated by avoiding a trip through the mark stack,
-              // by only doing a bookkeeping update and avoiding the
-              // actual scan of the object - a typeArray contains no
-              // references, and the metadata is built-in.
-              process_grey_object<false>(obj);
-            } else {
-              if (_cm->verbose_high()) {
-                gclog_or_tty->print_cr("[%u] below a finger (local: " PTR_FORMAT
-                                       ", global: " PTR_FORMAT ") pushing "
-                                       PTR_FORMAT " on mark stack",
-                                       _worker_id, p2i(_finger),
-                                       p2i(global_finger), p2i(objAddr));
-              }
-              push(obj);
-            }
-          }
-        }
+        make_reference_grey(obj, hr);
       }
     }
   }
--- a/hotspot/src/share/vm/gc_implementation/g1/concurrentMarkThread.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/concurrentMarkThread.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -192,7 +192,7 @@
       } else {
         // We don't want to update the marking status if a GC pause
         // is already underway.
-        SuspendibleThreadSetJoiner sts;
+        SuspendibleThreadSetJoiner sts_join;
         g1h->set_marking_complete();
       }
 
@@ -262,7 +262,7 @@
       // not needed any more as the concurrent mark state has been
       // already reset).
       {
-        SuspendibleThreadSetJoiner sts;
+        SuspendibleThreadSetJoiner sts_join;
         if (!cm()->has_aborted()) {
           g1_policy->record_concurrent_mark_cleanup_completed();
         }
@@ -291,7 +291,7 @@
     // Java thread is waiting for a full GC to happen (e.g., it
     // called System.gc() with +ExplicitGCInvokesConcurrent).
     {
-      SuspendibleThreadSetJoiner sts;
+      SuspendibleThreadSetJoiner sts_join;
       g1h->increment_old_marking_cycles_completed(true /* concurrent */);
       g1h->register_concurrent_cycle_end();
     }
--- a/hotspot/src/share/vm/gc_implementation/g1/evacuationInfo.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/evacuationInfo.hpp	Wed Jul 05 20:35:10 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
@@ -22,8 +22,8 @@
  *
  */
 
-#ifndef SHARE_VM_GC_IMPLEMENTATION_SHARED_EVACUATIONINFO_HPP
-#define SHARE_VM_GC_IMPLEMENTATION_SHARED_EVACUATIONINFO_HPP
+#ifndef SHARE_VM_GC_IMPLEMENTATION_G1_EVACUATIONINFO_HPP
+#define SHARE_VM_GC_IMPLEMENTATION_G1_EVACUATIONINFO_HPP
 
 #include "memory/allocation.hpp"
 
@@ -78,4 +78,4 @@
   uint   regions_freed()             { return _regions_freed; }
 };
 
-#endif // SHARE_VM_GC_IMPLEMENTATION_SHARED_EVACUATIONINFO_HPP
+#endif // SHARE_VM_GC_IMPLEMENTATION_G1_EVACUATIONINFO_HPP
--- a/hotspot/src/share/vm/gc_implementation/g1/g1Allocator.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1Allocator.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -24,7 +24,7 @@
 
 #include "precompiled.hpp"
 #include "gc_implementation/g1/g1Allocator.hpp"
-#include "gc_implementation/g1/g1CollectedHeap.hpp"
+#include "gc_implementation/g1/g1CollectedHeap.inline.hpp"
 #include "gc_implementation/g1/g1CollectorPolicy.hpp"
 #include "gc_implementation/g1/heapRegion.inline.hpp"
 #include "gc_implementation/g1/heapRegionSet.inline.hpp"
@@ -119,7 +119,6 @@
   size_t gclab_word_size = _g1h->desired_plab_sz(dest);
   if (word_sz * 100 < gclab_word_size * ParallelGCBufferWastePct) {
     G1PLAB* alloc_buf = alloc_buffer(dest, context);
-    add_to_alloc_buffer_waste(alloc_buf->words_remaining());
     alloc_buf->retire();
 
     HeapWord* buf = _g1h->par_allocate_during_gc(dest, gclab_word_size, context);
@@ -153,8 +152,19 @@
   for (uint state = 0; state < InCSetState::Num; state++) {
     G1PLAB* const buf = _alloc_buffers[state];
     if (buf != NULL) {
-      add_to_alloc_buffer_waste(buf->words_remaining());
       buf->flush_and_retire_stats(_g1h->alloc_buffer_stats(state));
     }
   }
 }
+
+void G1DefaultParGCAllocator::waste(size_t& wasted, size_t& undo_wasted) {
+  wasted = 0;
+  undo_wasted = 0;
+  for (uint state = 0; state < InCSetState::Num; state++) {
+    G1PLAB * const buf = _alloc_buffers[state];
+    if (buf != NULL) {
+      wasted += buf->waste();
+      undo_wasted += buf->undo_waste();
+    }
+  }
+}
--- a/hotspot/src/share/vm/gc_implementation/g1/g1Allocator.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1Allocator.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -188,12 +188,6 @@
   // architectures have a special compare against zero instructions.
   const uint _survivor_alignment_bytes;
 
-  size_t _alloc_buffer_waste;
-  size_t _undo_waste;
-
-  void add_to_alloc_buffer_waste(size_t waste) { _alloc_buffer_waste += waste; }
-  void add_to_undo_waste(size_t waste)         { _undo_waste += waste; }
-
   virtual void retire_alloc_buffers() = 0;
   virtual G1PLAB* alloc_buffer(InCSetState dest, AllocationContext_t context) = 0;
 
@@ -213,15 +207,12 @@
 
 public:
   G1ParGCAllocator(G1CollectedHeap* g1h) :
-    _g1h(g1h), _survivor_alignment_bytes(calc_survivor_alignment_bytes()),
-    _alloc_buffer_waste(0), _undo_waste(0) {
-  }
+    _g1h(g1h), _survivor_alignment_bytes(calc_survivor_alignment_bytes()) { }
   virtual ~G1ParGCAllocator() { }
 
   static G1ParGCAllocator* create_allocator(G1CollectedHeap* g1h);
 
-  size_t alloc_buffer_waste() { return _alloc_buffer_waste; }
-  size_t undo_waste() {return _undo_waste; }
+  virtual void waste(size_t& wasted, size_t& undo_wasted) = 0;
 
   // Allocate word_sz words in dest, either directly into the regions or by
   // allocating a new PLAB. Returns the address of the allocated memory, NULL if
@@ -253,14 +244,7 @@
   }
 
   void undo_allocation(InCSetState dest, HeapWord* obj, size_t word_sz, AllocationContext_t context) {
-    if (alloc_buffer(dest, context)->contains(obj)) {
-      assert(alloc_buffer(dest, context)->contains(obj + word_sz - 1),
-             "should contain whole object");
-      alloc_buffer(dest, context)->undo_allocation(obj, word_sz);
-    } else {
-      CollectedHeap::fill_with_object(obj, word_sz);
-      add_to_undo_waste(word_sz);
-    }
+    alloc_buffer(dest, context)->undo_allocation(obj, word_sz);
   }
 };
 
@@ -280,7 +264,9 @@
     return _alloc_buffers[dest.value()];
   }
 
-  virtual void retire_alloc_buffers() ;
+  virtual void retire_alloc_buffers();
+
+  virtual void waste(size_t& wasted, size_t& undo_wasted);
 };
 
 #endif // SHARE_VM_GC_IMPLEMENTATION_G1_G1ALLOCATOR_HPP
--- a/hotspot/src/share/vm/gc_implementation/g1/g1BlockOffsetTable.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1BlockOffsetTable.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -23,8 +23,8 @@
  */
 
 #include "precompiled.hpp"
-#include "gc_implementation/g1/g1CollectedHeap.hpp"
 #include "gc_implementation/g1/g1BlockOffsetTable.inline.hpp"
+#include "gc_implementation/g1/g1CollectedHeap.inline.hpp"
 #include "gc_implementation/g1/heapRegion.hpp"
 #include "memory/space.hpp"
 #include "oops/oop.inline.hpp"
@@ -66,6 +66,20 @@
   return (delta & right_n_bits(LogN_words)) == (size_t)NoBits;
 }
 
+#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,
+                 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
+                 " (%u) is not in committed area.",
+                 (index),
+                 p2i(address_for_index_raw(index)),
+                 G1CollectedHeap::heap()->addr_to_region(address_for_index_raw(index))));
+}
+#endif // ASSERT
+
 //////////////////////////////////////////////////////////////////////
 // G1BlockOffsetArray
 //////////////////////////////////////////////////////////////////////
--- a/hotspot/src/share/vm/gc_implementation/g1/g1BlockOffsetTable.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1BlockOffsetTable.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -170,6 +170,8 @@
 
   bool is_card_boundary(HeapWord* p) const;
 
+  void check_index(size_t index, const char* msg) const NOT_DEBUG_RETURN;
+
 public:
 
   // Return the number of slots needed for an offset array
@@ -179,6 +181,11 @@
     return ReservedSpace::allocation_align_size_up(number_of_slots);
   }
 
+  // Returns how many bytes of the heap a single byte of the BOT corresponds to.
+  static size_t heap_map_factor() {
+    return N_bytes;
+  }
+
   enum SomePublicConstants {
     LogN = 9,
     LogN_words = LogN - LogHeapWordSize,
--- a/hotspot/src/share/vm/gc_implementation/g1/g1BlockOffsetTable.inline.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1BlockOffsetTable.inline.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2001, 2014, 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
@@ -26,7 +26,6 @@
 #define SHARE_VM_GC_IMPLEMENTATION_G1_G1BLOCKOFFSETTABLE_INLINE_HPP
 
 #include "gc_implementation/g1/g1BlockOffsetTable.hpp"
-#include "gc_implementation/g1/g1CollectedHeap.inline.hpp"
 #include "gc_implementation/g1/heapRegion.inline.hpp"
 #include "memory/space.hpp"
 
@@ -47,17 +46,6 @@
   }
 }
 
-#define check_index(index, msg)                                                \
-  assert((index) < (_reserved.word_size() >> LogN_words),                      \
-         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             \
-                 " (%u) is not in committed area.",                            \
-                 (index),                                                      \
-                 p2i(address_for_index_raw(index)),                            \
-                 G1CollectedHeap::heap()->addr_to_region(address_for_index_raw(index))));
-
 u_char G1BlockOffsetSharedArray::offset_array(size_t index) const {
   check_index(index, "index out of range");
   return _offset_array[index];
@@ -119,8 +107,6 @@
   return result;
 }
 
-#undef check_index
-
 inline size_t
 G1BlockOffsetArray::block_size(const HeapWord* p) const {
   return gsp()->block_size(p);
--- a/hotspot/src/share/vm/gc_implementation/g1/g1CardCounts.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1CardCounts.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013, 2014, 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
@@ -39,6 +39,17 @@
   _counts->clear_range(mr);
 }
 
+size_t G1CardCounts::compute_size(size_t mem_region_size_in_words) {
+  // We keep card counts for every card, so the size of the card counts table must
+  // be the same as the card table.
+  return G1SATBCardTableLoggingModRefBS::compute_size(mem_region_size_in_words);
+}
+
+size_t G1CardCounts::heap_map_factor() {
+  // See G1CardCounts::compute_size() why we reuse the card table value.
+  return G1SATBCardTableLoggingModRefBS::heap_map_factor();
+}
+
 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,
--- a/hotspot/src/share/vm/gc_implementation/g1/g1CardCounts.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1CardCounts.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -101,6 +101,14 @@
  public:
   G1CardCounts(G1CollectedHeap* g1h);
 
+  // Return the number of slots needed for a card counts table
+  // that covers mem_region_words words.
+  static size_t compute_size(size_t mem_region_size_in_words);
+
+  // Returns how many bytes of the heap a single byte of the card counts table
+  // corresponds to.
+  static size_t heap_map_factor();
+
   void initialize(G1RegionToSpaceMapper* mapper);
 
   // Increments the refinement count for the given card.
--- a/hotspot/src/share/vm/gc_implementation/g1/g1CollectedHeap.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1CollectedHeap.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -66,6 +66,7 @@
 #include "runtime/vmThread.hpp"
 #include "utilities/globalDefinitions.hpp"
 #include "utilities/stack.inline.hpp"
+#include "utilities/taskqueue.inline.hpp"
 
 size_t G1CollectedHeap::_humongous_object_threshold_in_words = 0;
 
@@ -1083,11 +1084,9 @@
 class RebuildRSOutOfRegionClosure: public HeapRegionClosure {
   G1CollectedHeap*   _g1h;
   UpdateRSOopClosure _cl;
-  int                _worker_i;
 public:
-  RebuildRSOutOfRegionClosure(G1CollectedHeap* g1, int worker_i = 0) :
+  RebuildRSOutOfRegionClosure(G1CollectedHeap* g1, uint worker_i = 0) :
     _cl(g1->g1_rem_set(), worker_i),
-    _worker_i(worker_i),
     _g1h(g1)
   { }
 
@@ -1166,6 +1165,7 @@
   SvcGCMarker sgcm(SvcGCMarker::FULL);
   ResourceMark rm;
 
+  G1Log::update_level();
   print_heap_before_gc();
   trace_heap_before_gc(gc_tracer);
 
@@ -1877,37 +1877,42 @@
   // Carve out the G1 part of the heap.
 
   ReservedSpace g1_rs = heap_rs.first_part(max_byte_size);
+  size_t page_size = UseLargePages ? os::large_page_size() : os::vm_page_size();
   G1RegionToSpaceMapper* heap_storage =
     G1RegionToSpaceMapper::create_mapper(g1_rs,
                                          g1_rs.size(),
-                                         UseLargePages ? os::large_page_size() : os::vm_page_size(),
+                                         page_size,
                                          HeapRegion::GrainBytes,
                                          1,
                                          mtJavaHeap);
+  os::trace_page_sizes("G1 Heap", collector_policy()->min_heap_byte_size(),
+                       max_byte_size, page_size,
+                       heap_rs.base(),
+                       heap_rs.size());
   heap_storage->set_mapping_changed_listener(&_listener);
 
   // Create storage for the BOT, card table, card counts table (hot card cache) and the bitmaps.
   G1RegionToSpaceMapper* bot_storage =
     create_aux_memory_mapper("Block offset table",
                              G1BlockOffsetSharedArray::compute_size(g1_rs.size() / HeapWordSize),
-                             G1BlockOffsetSharedArray::N_bytes);
+                             G1BlockOffsetSharedArray::heap_map_factor());
 
   ReservedSpace cardtable_rs(G1SATBCardTableLoggingModRefBS::compute_size(g1_rs.size() / HeapWordSize));
   G1RegionToSpaceMapper* cardtable_storage =
     create_aux_memory_mapper("Card table",
                              G1SATBCardTableLoggingModRefBS::compute_size(g1_rs.size() / HeapWordSize),
-                             G1BlockOffsetSharedArray::N_bytes);
+                             G1SATBCardTableLoggingModRefBS::heap_map_factor());
 
   G1RegionToSpaceMapper* card_counts_storage =
     create_aux_memory_mapper("Card counts table",
-                             G1BlockOffsetSharedArray::compute_size(g1_rs.size() / HeapWordSize),
-                             G1BlockOffsetSharedArray::N_bytes);
+                             G1CardCounts::compute_size(g1_rs.size() / HeapWordSize),
+                             G1CardCounts::heap_map_factor());
 
   size_t bitmap_size = CMBitMap::compute_size(g1_rs.size());
   G1RegionToSpaceMapper* prev_bitmap_storage =
-    create_aux_memory_mapper("Prev Bitmap", bitmap_size, CMBitMap::mark_distance());
+    create_aux_memory_mapper("Prev Bitmap", bitmap_size, CMBitMap::heap_map_factor());
   G1RegionToSpaceMapper* next_bitmap_storage =
-    create_aux_memory_mapper("Next Bitmap", bitmap_size, CMBitMap::mark_distance());
+    create_aux_memory_mapper("Next Bitmap", bitmap_size, CMBitMap::heap_map_factor());
 
   _hrm.initialize(heap_storage, prev_bitmap_storage, next_bitmap_storage, bot_storage, cardtable_storage, card_counts_storage);
   g1_barrier_set()->initialize(cardtable_storage);
@@ -3039,7 +3044,7 @@
       assert(UseDynamicNumberOfGCThreads ||
         workers()->active_workers() == workers()->total_workers(),
         "If not dynamic should be using all the workers");
-      int n_workers = workers()->active_workers();
+      uint n_workers = workers()->active_workers();
       set_par_threads(n_workers);
       workers()->run_task(&task);
       set_par_threads(0);
@@ -3577,9 +3582,9 @@
   print_taskqueue_stats_hdr(st);
 
   TaskQueueStats totals;
-  const int n = workers()->total_workers();
-  for (int i = 0; i < n; ++i) {
-    st->print("%3d ", i); task_queue(i)->stats.print(st); st->cr();
+  const uint n = workers()->total_workers();
+  for (uint i = 0; i < n; ++i) {
+    st->print("%3u ", i); task_queue(i)->stats.print(st); st->cr();
     totals += task_queue(i)->stats;
   }
   st->print_raw("tot "); totals.print(st); st->cr();
@@ -3588,8 +3593,8 @@
 }
 
 void G1CollectedHeap::reset_taskqueue_stats() {
-  const int n = workers()->total_workers();
-  for (int i = 0; i < n; ++i) {
+  const uint n = workers()->total_workers();
+  for (uint i = 0; i < n; ++i) {
     task_queue(i)->stats.reset();
   }
 }
@@ -3648,6 +3653,7 @@
   SvcGCMarker sgcm(SvcGCMarker::MINOR);
   ResourceMark rm;
 
+  G1Log::update_level();
   print_heap_before_gc();
   trace_heap_before_gc(_gc_tracer_stw);
 
@@ -4318,7 +4324,7 @@
 
   ParallelTaskTerminator* terminator() { return &_terminator; }
 
-  virtual void set_for_termination(int active_workers) {
+  virtual void set_for_termination(uint active_workers) {
     _root_processor->set_num_workers(active_workers);
     terminator()->reset_for_reuse(active_workers);
     _n_workers = active_workers;
@@ -4997,13 +5003,13 @@
   G1CollectedHeap*   _g1h;
   RefToScanQueueSet* _queues;
   FlexibleWorkGang*  _workers;
-  int                _active_workers;
+  uint               _active_workers;
 
 public:
   G1STWRefProcTaskExecutor(G1CollectedHeap* g1h,
-                        FlexibleWorkGang* workers,
-                        RefToScanQueueSet *task_queues,
-                        int n_workers) :
+                           FlexibleWorkGang* workers,
+                           RefToScanQueueSet *task_queues,
+                           uint n_workers) :
     _g1h(g1h),
     _queues(task_queues),
     _workers(workers),
@@ -5136,7 +5142,7 @@
   uint _n_workers;
 
 public:
-  G1ParPreserveCMReferentsTask(G1CollectedHeap* g1h,int workers, RefToScanQueueSet *task_queues) :
+  G1ParPreserveCMReferentsTask(G1CollectedHeap* g1h, uint workers, RefToScanQueueSet *task_queues) :
     AbstractGangTask("ParPreserveCMReferents"),
     _g1h(g1h),
     _queues(task_queues),
--- a/hotspot/src/share/vm/gc_implementation/g1/g1CollectedHeap.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1CollectedHeap.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -979,7 +979,7 @@
 
   void set_refine_cte_cl_concurrency(bool concurrent);
 
-  RefToScanQueue *task_queue(int i) const;
+  RefToScanQueue *task_queue(uint i) const;
 
   // A set of cards where updates happened during the GC
   DirtyCardQueueSet& dirty_card_queue_set() { return _dirty_card_queue_set; }
--- a/hotspot/src/share/vm/gc_implementation/g1/g1CollectedHeap.inline.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1CollectedHeap.inline.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -210,7 +210,7 @@
   g1_barrier_set()->g1_mark_as_young(mr);
 }
 
-inline RefToScanQueue* G1CollectedHeap::task_queue(int i) const {
+inline RefToScanQueue* G1CollectedHeap::task_queue(uint i) const {
   return _task_queues->queue(i);
 }
 
--- a/hotspot/src/share/vm/gc_implementation/g1/g1GCPhaseTimes.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1GCPhaseTimes.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -22,8 +22,8 @@
  *
  */
 
-#ifndef SHARE_VM_GC_IMPLEMENTATION_G1_G1GCPHASETIMESLOG_HPP
-#define SHARE_VM_GC_IMPLEMENTATION_G1_G1GCPHASETIMESLOG_HPP
+#ifndef SHARE_VM_GC_IMPLEMENTATION_G1_G1GCPHASETIMES_HPP
+#define SHARE_VM_GC_IMPLEMENTATION_G1_G1GCPHASETIMES_HPP
 
 #include "memory/allocation.hpp"
 
@@ -286,4 +286,4 @@
   ~G1GCParPhaseTimesTracker();
 };
 
-#endif // SHARE_VM_GC_IMPLEMENTATION_G1_G1GCPHASETIMESLOG_HPP
+#endif // SHARE_VM_GC_IMPLEMENTATION_G1_G1GCPHASETIMES_HPP
--- a/hotspot/src/share/vm/gc_implementation/g1/g1Log.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1Log.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, 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
@@ -25,17 +25,34 @@
 #include "precompiled.hpp"
 #include "gc_implementation/g1/g1_globals.hpp"
 #include "gc_implementation/g1/g1Log.hpp"
-#include "runtime/globals.hpp"
+#include "runtime/globals_extension.hpp"
 
 G1Log::LogLevel G1Log::_level = G1Log::LevelNone;
 
+
+// Updates _level based on PrintGC and PrintGCDetails values (unless
+// G1LogLevel is set explicitly)
+// - PrintGC maps to "fine".
+// - PrintGCDetails maps to "finer".
+void G1Log::update_level() {
+  if (FLAG_IS_DEFAULT(G1LogLevel)) {
+    _level = LevelNone;
+    if (PrintGCDetails) {
+      _level = LevelFiner;
+    } else if (PrintGC) {
+      _level = LevelFine;
+    }
+  }
+}
+
+
 // If G1LogLevel has not been set up we will use the values of PrintGC
 // and PrintGCDetails for the logging level.
-// - PrintGC maps to "fine".
-// - PrintGCDetails maps to "finer".
 void G1Log::init() {
-  if (G1LogLevel != NULL && G1LogLevel[0] != '\0') {
-    if (strncmp("none", G1LogLevel, 4) == 0 && G1LogLevel[4] == '\0') {
+  if (!FLAG_IS_DEFAULT(G1LogLevel)) {
+    // PrintGC flags change won't have any affect, because G1LogLevel
+    // is set explicitly
+    if (G1LogLevel[0] == '\0' || strncmp("none", G1LogLevel, 4) == 0 && G1LogLevel[4] == '\0') {
       _level = LevelNone;
     } else if (strncmp("fine", G1LogLevel, 4) == 0 && G1LogLevel[4] == '\0') {
       _level = LevelFine;
@@ -47,10 +64,7 @@
       warning("Unknown logging level '%s', should be one of 'fine', 'finer' or 'finest'.", G1LogLevel);
     }
   } else {
-    if (PrintGCDetails) {
-      _level = LevelFiner;
-    } else if (PrintGC) {
-      _level = LevelFine;
-    }
+    update_level();
   }
 }
+
--- a/hotspot/src/share/vm/gc_implementation/g1/g1Log.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1Log.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, 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
@@ -57,6 +57,9 @@
   }
 
   static void init();
+
+  // Update to log level to reflect runtime changes to manageable flags
+  static void update_level();
 };
 
 #endif // SHARE_VM_GC_IMPLEMENTATION_G1_G1LOG_HPP
--- a/hotspot/src/share/vm/gc_implementation/g1/g1MMUTracker.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1MMUTracker.cpp	Wed Jul 05 20:35:10 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
@@ -76,9 +76,6 @@
 }
 
 void G1MMUTrackerQueue::add_pause(double start, double end, bool gc_thread) {
-  double longest_allowed = longest_pause_internal(start);
-  if (longest_allowed < 0.0)
-    longest_allowed = 0.0;
   double duration = end - start;
 
   remove_expired_entries(end);
@@ -111,41 +108,6 @@
 // this is for trying things out in the future and a couple
 // of other places (debugging)
 
-double G1MMUTrackerQueue::longest_pause(double current_time) {
-  if (_DISABLE_MMU)
-    return _max_gc_time;
-
-  MutexLockerEx x(MMUTracker_lock, Mutex::_no_safepoint_check_flag);
-  remove_expired_entries(current_time);
-
-  return longest_pause_internal(current_time);
-}
-
-double G1MMUTrackerQueue::longest_pause_internal(double current_time) {
-  double target_time = _max_gc_time;
-
-  while( 1 ) {
-    double gc_time =
-      calculate_gc_time(current_time + target_time);
-    double diff = target_time + gc_time - _max_gc_time;
-    if (!is_double_leq_0(diff)) {
-      target_time -= diff;
-      if (is_double_leq_0(target_time)) {
-        target_time = -1.0;
-        break;
-      }
-    } else {
-      break;
-    }
-  }
-
-  return target_time;
-}
-
-// basically the _internal call does not remove expired entries
-// this is for trying things out in the future and a couple
-// of other places (debugging)
-
 double G1MMUTrackerQueue::when_sec(double current_time, double pause_time) {
   if (_DISABLE_MMU)
     return 0.0;
--- a/hotspot/src/share/vm/gc_implementation/g1/g1MMUTracker.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1MMUTracker.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2001, 2012, 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,6 @@
   G1MMUTracker(double time_slice, double max_gc_time);
 
   virtual void add_pause(double start, double end, bool gc_thread) = 0;
-  virtual double longest_pause(double current_time) = 0;
   virtual double when_sec(double current_time, double pause_time) = 0;
 
   double max_gc_time() {
@@ -122,7 +121,6 @@
   void remove_expired_entries(double current_time);
   double calculate_gc_time(double current_time);
 
-  double longest_pause_internal(double current_time);
   double when_internal(double current_time, double pause_time);
 
 public:
@@ -130,7 +128,6 @@
 
   virtual void add_pause(double start, double end, bool gc_thread);
 
-  virtual double longest_pause(double current_time);
   virtual double when_sec(double current_time, double pause_time);
 };
 
--- a/hotspot/src/share/vm/gc_implementation/g1/g1ParScanThreadState.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1ParScanThreadState.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -29,7 +29,7 @@
 #include "gc_implementation/g1/g1StringDedup.hpp"
 #include "oops/oop.inline.hpp"
 #include "runtime/prefetch.inline.hpp"
-#include "utilities/stack.inline.hpp"
+#include "utilities/taskqueue.inline.hpp"
 
 G1ParScanThreadState::G1ParScanThreadState(G1CollectedHeap* g1h, uint queue_num, ReferenceProcessor* rp)
   : _g1h(g1h),
@@ -95,8 +95,9 @@
   const double elapsed_ms = elapsed_time() * 1000.0;
   const double s_roots_ms = strong_roots_time() * 1000.0;
   const double term_ms    = term_time() * 1000.0;
-  const size_t alloc_buffer_waste = _g1_par_allocator->alloc_buffer_waste();
-  const size_t undo_waste         = _g1_par_allocator->undo_waste();
+  size_t alloc_buffer_waste = 0;
+  size_t undo_waste = 0;
+  _g1_par_allocator->waste(alloc_buffer_waste, undo_waste);
   st->print_cr("%3d %9.2f %9.2f %6.2f "
                "%9.2f %6.2f " SIZE_FORMAT_W(8) " "
                SIZE_FORMAT_W(7) " " SIZE_FORMAT_W(7) " " SIZE_FORMAT_W(7),
--- a/hotspot/src/share/vm/gc_implementation/g1/g1ParScanThreadState.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1ParScanThreadState.hpp	Wed Jul 05 20:35:10 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
@@ -54,9 +54,6 @@
   uint              _tenuring_threshold;
   G1ParScanClosure  _scanner;
 
-  size_t            _alloc_buffer_waste;
-  size_t            _undo_waste;
-
   OopsInHeapRegionClosure*      _evac_failure_cl;
 
   int  _hash_seed;
@@ -78,9 +75,6 @@
 
 #define PADDING_ELEM_NUM (DEFAULT_CACHE_LINE_SIZE / sizeof(size_t))
 
-  void   add_to_alloc_buffer_waste(size_t waste) { _alloc_buffer_waste += waste; }
-  void   add_to_undo_waste(size_t waste)         { _undo_waste += waste; }
-
   DirtyCardQueue& dirty_card_queue()             { return _dcq;  }
   G1SATBCardTableModRefBS* ctbs()                { return _ct_bs; }
 
@@ -106,10 +100,7 @@
   bool verify_task(StarTask ref) const;
 #endif // ASSERT
 
-  template <class T> void push_on_queue(T* ref) {
-    assert(verify_ref(ref), "sanity");
-    _refs->push(ref);
-  }
+  template <class T> void push_on_queue(T* ref);
 
   template <class T> void update_rs(HeapRegion* from, T* p, uint tid) {
     // If the new value of the field points to the same region or
--- a/hotspot/src/share/vm/gc_implementation/g1/g1ParScanThreadState.inline.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1ParScanThreadState.inline.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -59,6 +59,11 @@
   update_rs(from, p, queue_num());
 }
 
+template <class T> inline void G1ParScanThreadState::push_on_queue(T* ref) {
+  assert(verify_ref(ref), "sanity");
+  _refs->push(ref);
+}
+
 inline void G1ParScanThreadState::do_oop_partial_array(oop* p) {
   assert(has_partial_array_mask(p), "invariant");
   oop from_obj = clear_partial_array_mask(p);
--- a/hotspot/src/share/vm/gc_implementation/g1/g1RootProcessor.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1RootProcessor.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -329,6 +329,6 @@
   _g1h->g1_rem_set()->oops_into_collection_set_do(scan_rs, &scavenge_cs_nmethods, worker_i);
 }
 
-void G1RootProcessor::set_num_workers(int active_workers) {
+void G1RootProcessor::set_num_workers(uint active_workers) {
   _process_strong_tasks->set_n_threads(active_workers);
 }
--- a/hotspot/src/share/vm/gc_implementation/g1/g1RootProcessor.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1RootProcessor.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -22,8 +22,8 @@
  *
  */
 
-#ifndef SHARE_VM_GC_IMPLEMENTATION_G1_ROOTPROCESSOR_HPP
-#define SHARE_VM_GC_IMPLEMENTATION_G1_ROOTPROCESSOR_HPP
+#ifndef SHARE_VM_GC_IMPLEMENTATION_G1_G1ROOTPROCESSOR_HPP
+#define SHARE_VM_GC_IMPLEMENTATION_G1_G1ROOTPROCESSOR_HPP
 
 #include "memory/allocation.hpp"
 #include "memory/strongRootsScope.hpp"
@@ -115,7 +115,7 @@
                             uint worker_i);
 
   // Inform the root processor about the number of worker threads
-  void set_num_workers(int active_workers);
+  void set_num_workers(uint active_workers);
 };
 
-#endif // SHARE_VM_GC_IMPLEMENTATION_G1_ROOTPROCESSOR_HPP
+#endif // SHARE_VM_GC_IMPLEMENTATION_G1_G1ROOTPROCESSOR_HPP
--- a/hotspot/src/share/vm/gc_implementation/g1/g1SATBCardTableModRefBS.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1SATBCardTableModRefBS.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -153,6 +153,11 @@
     return ReservedSpace::allocation_align_size_up(number_of_slots);
   }
 
+  // Returns how many bytes of the heap a single byte of the Card Table corresponds to.
+  static size_t heap_map_factor() {
+    return CardTableModRefBS::card_size;
+  }
+
   G1SATBCardTableLoggingModRefBS(MemRegion whole_heap);
 
   virtual void initialize() { }
--- a/hotspot/src/share/vm/gc_implementation/g1/g1StringDedupTable.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1StringDedupTable.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -310,11 +310,11 @@
     // Compute hash
     hash = hash_code(value);
     stat.inc_hashed();
-  }
 
-  if (use_java_hash() && hash != 0) {
-    // Store hash code in cache
-    java_lang_String::set_hash(java_string, hash);
+    if (use_java_hash() && hash != 0) {
+      // Store hash code in cache
+      java_lang_String::set_hash(java_string, hash);
+    }
   }
 
   typeArrayOop existing_value = lookup_or_add(value, hash);
--- a/hotspot/src/share/vm/gc_implementation/g1/g1StringDedupThread.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1StringDedupThread.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -74,7 +74,7 @@
 
     {
       // Include thread in safepoints
-      SuspendibleThreadSetJoiner sts;
+      SuspendibleThreadSetJoiner sts_join;
 
       stat.mark_exec();
 
@@ -88,9 +88,9 @@
         G1StringDedupTable::deduplicate(java_string, stat);
 
         // Safepoint this thread if needed
-        if (sts.should_yield()) {
+        if (sts_join.should_yield()) {
           stat.mark_block();
-          sts.yield();
+          sts_join.yield();
           stat.mark_unblock();
         }
       }
--- a/hotspot/src/share/vm/gc_implementation/g1/heapRegionBounds.inline.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/heapRegionBounds.inline.hpp	Wed Jul 05 20:35:10 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
@@ -22,6 +22,9 @@
  *
  */
 
+#ifndef SHARE_VM_GC_IMPLEMENTATION_G1_HEAPREGIONBOUNDS_INLINE_HPP
+#define SHARE_VM_GC_IMPLEMENTATION_G1_HEAPREGIONBOUNDS_INLINE_HPP
+
 #include "gc_implementation/g1/heapRegionBounds.hpp"
 
 size_t HeapRegionBounds::min_size() {
@@ -35,3 +38,5 @@
 size_t HeapRegionBounds::target_number() {
   return TARGET_REGION_NUMBER;
 }
+
+#endif // SHARE_VM_GC_IMPLEMENTATION_G1_HEAPREGIONBOUNDS_INLINE_HPP
--- a/hotspot/src/share/vm/gc_implementation/g1/satbQueue.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/satbQueue.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -29,6 +29,7 @@
 #include "memory/allocation.inline.hpp"
 #include "oops/oop.inline.hpp"
 #include "runtime/mutexLocker.hpp"
+#include "runtime/safepoint.hpp"
 #include "runtime/thread.hpp"
 #include "runtime/vmThread.hpp"
 
@@ -160,10 +161,7 @@
   assert(_lock == NULL || _lock->owned_by_self(),
          "we should have taken the lock before calling this");
 
-  // Even if G1SATBBufferEnqueueingThresholdPercent == 0 we have to
-  // filter the buffer given that this will remove any references into
-  // the CSet as we currently assume that no such refs will appear in
-  // enqueued buffers.
+  // If G1SATBBufferEnqueueingThresholdPercent == 0 we could skip filtering.
 
   // This method should only be called if there is a non-NULL buffer
   // that is full.
@@ -180,25 +178,19 @@
   return should_enqueue;
 }
 
-void ObjPtrQueue::apply_closure_and_empty(ObjectClosure* cl) {
+void ObjPtrQueue::apply_closure_and_empty(SATBBufferClosure* cl) {
+  assert(SafepointSynchronize::is_at_safepoint(),
+         "SATB queues must only be processed at safepoints");
   if (_buf != NULL) {
-    apply_closure_to_buffer(cl, _buf, _index, _sz);
+    assert(_index % sizeof(void*) == 0, "invariant");
+    assert(_sz % sizeof(void*) == 0, "invariant");
+    assert(_index <= _sz, "invariant");
+    cl->do_buffer(_buf + byte_index_to_index((int)_index),
+                  byte_index_to_index((int)(_sz - _index)));
     _index = _sz;
   }
 }
 
-void ObjPtrQueue::apply_closure_to_buffer(ObjectClosure* cl,
-                                          void** buf, size_t index, size_t sz) {
-  if (cl == NULL) return;
-  for (size_t i = index; i < sz; i += oopSize) {
-    oop obj = (oop)buf[byte_index_to_index((int)i)];
-    // There can be NULL entries because of destructors.
-    if (obj != NULL) {
-      cl->do_object(obj);
-    }
-  }
-}
-
 #ifndef PRODUCT
 // Helpful for debugging
 
@@ -289,7 +281,7 @@
   shared_satb_queue()->filter();
 }
 
-bool SATBMarkQueueSet::apply_closure_to_completed_buffer(ObjectClosure* cl) {
+bool SATBMarkQueueSet::apply_closure_to_completed_buffer(SATBBufferClosure* cl) {
   BufferNode* nd = NULL;
   {
     MutexLockerEx x(_cbl_mon, Mutex::_no_safepoint_check_flag);
@@ -303,7 +295,18 @@
   }
   if (nd != NULL) {
     void **buf = BufferNode::make_buffer_from_node(nd);
-    ObjPtrQueue::apply_closure_to_buffer(cl, buf, 0, _sz);
+    // Skip over NULL entries at beginning (e.g. push end) of buffer.
+    // Filtering can result in non-full completed buffers; see
+    // should_enqueue_buffer.
+    assert(_sz % sizeof(void*) == 0, "invariant");
+    size_t limit = ObjPtrQueue::byte_index_to_index((int)_sz);
+    for (size_t i = 0; i < limit; ++i) {
+      if (buf[i] != NULL) {
+        // Found the end of the block of NULLs; process the remainder.
+        cl->do_buffer(buf + i, limit - i);
+        break;
+      }
+    }
     deallocate_buffer(buf);
     return true;
   } else {
--- a/hotspot/src/share/vm/gc_implementation/g1/satbQueue.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/g1/satbQueue.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -25,29 +25,30 @@
 #ifndef SHARE_VM_GC_IMPLEMENTATION_G1_SATBQUEUE_HPP
 #define SHARE_VM_GC_IMPLEMENTATION_G1_SATBQUEUE_HPP
 
+#include "memory/allocation.hpp"
 #include "gc_implementation/g1/ptrQueue.hpp"
 
-class ObjectClosure;
 class JavaThread;
 class SATBMarkQueueSet;
 
+// Base class for processing the contents of a SATB buffer.
+class SATBBufferClosure : public StackObj {
+protected:
+  ~SATBBufferClosure() { }
+
+public:
+  // Process the SATB entries in the designated buffer range.
+  virtual void do_buffer(void** buffer, size_t size) = 0;
+};
+
 // A ptrQueue whose elements are "oops", pointers to object heads.
 class ObjPtrQueue: public PtrQueue {
-  friend class Threads;
   friend class SATBMarkQueueSet;
-  friend class G1RemarkThreadsClosure;
 
 private:
   // Filter out unwanted entries from the buffer.
   void filter();
 
-  // Apply the closure to all elements and empty the buffer;
-  void apply_closure_and_empty(ObjectClosure* cl);
-
-  // Apply the closure to all elements of "buf", down to "index" (inclusive.)
-  static void apply_closure_to_buffer(ObjectClosure* cl,
-                                      void** buf, size_t index, size_t sz);
-
 public:
   ObjPtrQueue(PtrQueueSet* qset, bool perm = false) :
     // SATB queues are only active during marking cycles. We create
@@ -60,6 +61,10 @@
   // Process queue entries and free resources.
   void flush();
 
+  // Apply cl to the active part of the buffer.
+  // Prerequisite: Must be at a safepoint.
+  void apply_closure_and_empty(SATBBufferClosure* cl);
+
   // Overrides PtrQueue::should_enqueue_buffer(). See the method's
   // definition for more information.
   virtual bool should_enqueue_buffer();
@@ -97,10 +102,12 @@
   // Filter all the currently-active SATB buffers.
   void filter_thread_buffers();
 
-  // If there exists some completed buffer, pop it, then apply the
-  // closure to all its elements, and return true.  If no
-  // completed buffers exist, return false.
-  bool apply_closure_to_completed_buffer(ObjectClosure* closure);
+  // If there exists some completed buffer, pop and process it, and
+  // return true.  Otherwise return false.  Processing a buffer
+  // consists of applying the closure to the buffer range starting
+  // with the first non-NULL entry to the end of the buffer; the
+  // leading entries may be NULL due to filtering.
+  bool apply_closure_to_completed_buffer(SATBBufferClosure* cl);
 
 #ifndef PRODUCT
   // Helpful for debugging
--- a/hotspot/src/share/vm/gc_implementation/parNew/parNewGeneration.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/parNew/parNewGeneration.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -54,6 +54,7 @@
 #include "utilities/copy.hpp"
 #include "utilities/globalDefinitions.hpp"
 #include "utilities/stack.inline.hpp"
+#include "utilities/taskqueue.inline.hpp"
 #include "utilities/workgroup.hpp"
 
 #ifdef _MSC_VER
@@ -272,16 +273,8 @@
 }
 
 
-void ParScanThreadState::undo_alloc_in_to_space(HeapWord* obj,
-                                                size_t word_sz) {
-  // Is the alloc in the current alloc buffer?
-  if (to_space_alloc_buffer()->contains(obj)) {
-    assert(to_space_alloc_buffer()->contains(obj + word_sz - 1),
-           "Should contain whole object.");
-    to_space_alloc_buffer()->undo_allocation(obj, word_sz);
-  } else {
-    CollectedHeap::fill_with_object(obj, word_sz);
-  }
+void ParScanThreadState::undo_alloc_in_to_space(HeapWord* obj, size_t word_sz) {
+  to_space_alloc_buffer()->undo_allocation(obj, word_sz);
 }
 
 void ParScanThreadState::print_promotion_failure_size() {
@@ -308,7 +301,7 @@
   inline ParScanThreadState& thread_state(int i);
 
   void trace_promotion_failed(const YoungGCTracer* gc_tracer);
-  void reset(int active_workers, bool promotion_failed);
+  void reset(uint active_workers, bool promotion_failed);
   void flush();
 
   #if TASKQUEUE_STATS
@@ -365,7 +358,7 @@
   }
 }
 
-void ParScanThreadStateSet::reset(int active_threads, bool promotion_failed)
+void ParScanThreadStateSet::reset(uint active_threads, bool promotion_failed)
 {
   _term.reset_for_reuse(active_threads);
   if (promotion_failed) {
@@ -583,7 +576,7 @@
 
 // Reset the terminator for the given number of
 // active threads.
-void ParNewGenTask::set_for_termination(int active_workers) {
+void ParNewGenTask::set_for_termination(uint active_workers) {
   _state_set->reset(active_workers, _gen->promotion_failed());
   // Should the heap be passed in?  There's only 1 for now so
   // grab it instead.
@@ -766,7 +759,7 @@
 
 private:
   virtual void work(uint worker_id);
-  virtual void set_for_termination(int active_workers) {
+  virtual void set_for_termination(uint active_workers) {
     _state_set.terminator()->reset_for_reuse(active_workers);
   }
 private:
@@ -912,10 +905,10 @@
   AdaptiveSizePolicy* size_policy = gch->gen_policy()->size_policy();
   FlexibleWorkGang* workers = gch->workers();
   assert(workers != NULL, "Need workgang for parallel work");
-  int active_workers =
-      AdaptiveSizePolicy::calc_active_workers(workers->total_workers(),
-                                   workers->active_workers(),
-                                   Threads::number_of_non_daemon_threads());
+  uint active_workers =
+       AdaptiveSizePolicy::calc_active_workers(workers->total_workers(),
+                                               workers->active_workers(),
+                                               Threads::number_of_non_daemon_threads());
   workers->set_active_workers(active_workers);
   _old_gen = gch->old_gen();
 
@@ -947,7 +940,7 @@
 
   gch->save_marks();
   assert(workers != NULL, "Need parallel worker threads.");
-  int n_workers = active_workers;
+  uint n_workers = active_workers;
 
   // Set the correct parallelism (number of queues) in the reference processor
   ref_processor()->set_active_mt_degree(n_workers);
--- a/hotspot/src/share/vm/gc_implementation/parNew/parNewGeneration.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/parNew/parNewGeneration.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -250,7 +250,7 @@
 
   // Reset the terminator in ParScanThreadStateSet for
   // "active_workers" threads.
-  virtual void set_for_termination(int active_workers);
+  virtual void set_for_termination(uint active_workers);
 };
 
 class KeepAliveClosure: public DefNewGeneration::KeepAliveClosure {
--- a/hotspot/src/share/vm/gc_implementation/parallelScavenge/pcTasks.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/parallelScavenge/pcTasks.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -57,7 +57,7 @@
   ParCompactionManager* cm =
     ParCompactionManager::gc_thread_compaction_manager(which);
 
-  PSParallelCompact::MarkAndPushClosure mark_and_push_closure(cm);
+  ParCompactionManager::MarkAndPushClosure mark_and_push_closure(cm);
   CLDToOopClosure mark_and_push_from_clds(&mark_and_push_closure, true);
   MarkingCodeBlobClosure mark_and_push_in_blobs(&mark_and_push_closure, !CodeBlobToOopClosure::FixRelocations);
 
@@ -85,8 +85,8 @@
     PrintGCDetails && TraceParallelOldGCTasks, true, NULL, PSParallelCompact::gc_tracer()->gc_id()));
   ParCompactionManager* cm =
     ParCompactionManager::gc_thread_compaction_manager(which);
-  PSParallelCompact::MarkAndPushClosure mark_and_push_closure(cm);
-  PSParallelCompact::FollowKlassClosure follow_klass_closure(&mark_and_push_closure);
+  ParCompactionManager::MarkAndPushClosure mark_and_push_closure(cm);
+  ParCompactionManager::FollowKlassClosure follow_klass_closure(&mark_and_push_closure);
 
   switch (_root_type) {
     case universe:
@@ -156,8 +156,8 @@
     PrintGCDetails && TraceParallelOldGCTasks, true, NULL, PSParallelCompact::gc_tracer()->gc_id()));
   ParCompactionManager* cm =
     ParCompactionManager::gc_thread_compaction_manager(which);
-  PSParallelCompact::MarkAndPushClosure mark_and_push_closure(cm);
-  PSParallelCompact::FollowStackClosure follow_stack_closure(cm);
+  ParCompactionManager::MarkAndPushClosure mark_and_push_closure(cm);
+  ParCompactionManager::FollowStackClosure follow_stack_closure(cm);
   _rp_task.work(_work_id, *PSParallelCompact::is_alive_closure(),
                 mark_and_push_closure, follow_stack_closure);
 }
@@ -213,7 +213,7 @@
 
   ParCompactionManager* cm =
     ParCompactionManager::gc_thread_compaction_manager(which);
-  PSParallelCompact::MarkAndPushClosure mark_and_push_closure(cm);
+  ParCompactionManager::MarkAndPushClosure mark_and_push_closure(cm);
 
   oop obj = NULL;
   ObjArrayTask task;
--- a/hotspot/src/share/vm/gc_implementation/parallelScavenge/psCompactionManager.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/parallelScavenge/psCompactionManager.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -37,7 +37,7 @@
 #include "oops/objArrayKlass.inline.hpp"
 #include "oops/oop.inline.hpp"
 #include "runtime/atomic.inline.hpp"
-#include "utilities/stack.inline.hpp"
+#include "utilities/taskqueue.inline.hpp"
 
 PSOldGen*            ParCompactionManager::_old_gen = NULL;
 ParCompactionManager**  ParCompactionManager::_manager_array = NULL;
@@ -179,11 +179,11 @@
 void InstanceKlass::oop_pc_follow_contents(oop obj, ParCompactionManager* cm) {
   assert(obj != NULL, "can't follow the content of NULL object");
 
-  PSParallelCompact::follow_klass(cm, this);
+  cm->follow_klass(this);
   // Only mark the header and let the scan of the meta-data mark
   // everything else.
 
-  PSParallelCompact::MarkAndPushClosure cl(cm);
+  ParCompactionManager::MarkAndPushClosure cl(cm);
   InstanceKlass::oop_oop_iterate_oop_maps<true>(obj, &cl);
 }
 
@@ -201,9 +201,9 @@
     // the call to follow_class_loader is made when the class loader itself
     // is handled.
     if (klass->oop_is_instance() && InstanceKlass::cast(klass)->is_anonymous()) {
-      PSParallelCompact::follow_class_loader(cm, klass->class_loader_data());
+      cm->follow_class_loader(klass->class_loader_data());
     } else {
-      PSParallelCompact::follow_klass(cm, klass);
+      cm->follow_klass(klass);
     }
   } else {
     // If klass is NULL then this a mirror for a primitive type.
@@ -212,7 +212,7 @@
     assert(java_lang_Class::is_primitive(obj), "Sanity check");
   }
 
-  PSParallelCompact::MarkAndPushClosure cl(cm);
+  ParCompactionManager::MarkAndPushClosure cl(cm);
   oop_oop_iterate_statics<true>(obj, &cl);
 }
 
@@ -221,7 +221,7 @@
 
   ClassLoaderData * const loader_data = java_lang_ClassLoader::loader_data(obj);
   if (loader_data != NULL) {
-    PSParallelCompact::follow_class_loader(cm, loader_data);
+    cm->follow_class_loader(loader_data);
   }
 }
 
@@ -253,37 +253,24 @@
           gclog_or_tty->print_cr("       Non NULL normal " PTR_FORMAT, p2i(obj));
         }
       )
-      PSParallelCompact::mark_and_push(cm, referent_addr);
+      cm->mark_and_push(referent_addr);
     }
   }
   T* next_addr = (T*)java_lang_ref_Reference::next_addr(obj);
-  if (ReferenceProcessor::pending_list_uses_discovered_field()) {
-    // Treat discovered as normal oop, if ref is not "active",
-    // i.e. if next is non-NULL.
-    T  next_oop = oopDesc::load_heap_oop(next_addr);
-    if (!oopDesc::is_null(next_oop)) { // i.e. ref is not "active"
-      T* discovered_addr = (T*)java_lang_ref_Reference::discovered_addr(obj);
-      debug_only(
-        if(TraceReferenceGC && PrintGCDetails) {
-          gclog_or_tty->print_cr("   Process discovered as normal "
-                                 PTR_FORMAT, p2i(discovered_addr));
-        }
-      )
-      PSParallelCompact::mark_and_push(cm, discovered_addr);
-    }
-  } else {
-#ifdef ASSERT
-    // In the case of older JDKs which do not use the discovered
-    // field for the pending list, an inactive ref (next != NULL)
-    // must always have a NULL discovered field.
-    T next = oopDesc::load_heap_oop(next_addr);
-    oop discovered = java_lang_ref_Reference::discovered(obj);
-    assert(oopDesc::is_null(next) || oopDesc::is_null(discovered),
-           err_msg("Found an inactive reference " PTR_FORMAT " with a non-NULL discovered field",
-                   p2i(obj)));
-#endif
+  // Treat discovered as normal oop, if ref is not "active",
+  // i.e. if next is non-NULL.
+  T  next_oop = oopDesc::load_heap_oop(next_addr);
+  if (!oopDesc::is_null(next_oop)) { // i.e. ref is not "active"
+    T* discovered_addr = (T*)java_lang_ref_Reference::discovered_addr(obj);
+    debug_only(
+      if(TraceReferenceGC && PrintGCDetails) {
+        gclog_or_tty->print_cr("   Process discovered as normal "
+                               PTR_FORMAT, p2i(discovered_addr));
+      }
+    )
+    cm->mark_and_push(discovered_addr);
   }
-  PSParallelCompact::mark_and_push(cm, next_addr);
+  cm->mark_and_push(next_addr);
   klass->InstanceKlass::oop_pc_follow_contents(obj, cm);
 }
 
@@ -297,7 +284,7 @@
 }
 
 void ObjArrayKlass::oop_pc_follow_contents(oop obj, ParCompactionManager* cm) {
-  PSParallelCompact::follow_klass(cm, this);
+  cm->follow_klass(this);
 
   if (UseCompressedOops) {
     oop_pc_follow_contents_specialized<narrowOop>(objArrayOop(obj), 0, cm);
--- a/hotspot/src/share/vm/gc_implementation/parallelScavenge/psCompactionManager.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/parallelScavenge/psCompactionManager.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -29,11 +29,6 @@
 #include "utilities/stack.hpp"
 #include "utilities/taskqueue.hpp"
 
-// Move to some global location
-#define HAS_BEEN_MOVED 0x1501d01d
-// End move to some global location
-
-
 class MutableSpace;
 class PSOldGen;
 class ParCompactionManager;
@@ -170,24 +165,23 @@
   bool should_copy();
 
   // Save for later processing.  Must not fail.
-  inline void push(oop obj) { _marking_stack.push(obj); }
+  inline void push(oop obj);
   inline void push_objarray(oop objarray, size_t index);
   inline void push_region(size_t index);
 
+  // Check mark and maybe push on marking stack.
+  template <typename T> inline void mark_and_push(T* p);
+
+  inline void follow_klass(Klass* klass);
+
+  void follow_class_loader(ClassLoaderData* klass);
+
   // Access function for compaction managers
   static ParCompactionManager* gc_thread_compaction_manager(int index);
 
-  static bool steal(int queue_num, int* seed, oop& t) {
-    return stack_array()->steal(queue_num, seed, t);
-  }
-
-  static bool steal_objarray(int queue_num, int* seed, ObjArrayTask& t) {
-    return _objarray_queues->steal(queue_num, seed, t);
-  }
-
-  static bool steal(int queue_num, int* seed, size_t& region) {
-    return region_array()->steal(queue_num, seed, region);
-  }
+  static bool steal(int queue_num, int* seed, oop& t);
+  static bool steal_objarray(int queue_num, int* seed, ObjArrayTask& t);
+  static bool steal(int queue_num, int* seed, size_t& region);
 
   // Process tasks remaining on any marking stack
   void follow_marking_stacks();
@@ -200,6 +194,39 @@
   void follow_contents(objArrayOop array, int index);
 
   void update_contents(oop obj);
+
+  class MarkAndPushClosure: public ExtendedOopClosure {
+   private:
+    ParCompactionManager* _compaction_manager;
+   public:
+    MarkAndPushClosure(ParCompactionManager* cm) : _compaction_manager(cm) { }
+
+    template <typename T> void do_oop_nv(T* p);
+    virtual void do_oop(oop* p);
+    virtual void do_oop(narrowOop* p);
+
+    // This closure provides its own oop verification code.
+    debug_only(virtual bool should_verify_oops() { return false; })
+  };
+
+  class FollowStackClosure: public VoidClosure {
+   private:
+    ParCompactionManager* _compaction_manager;
+   public:
+    FollowStackClosure(ParCompactionManager* cm) : _compaction_manager(cm) { }
+    virtual void do_void();
+  };
+
+  // The one and only place to start following the classes.
+  // Should only be applied to the ClassLoaderData klasses list.
+  class FollowKlassClosure : public KlassClosure {
+   private:
+    MarkAndPushClosure* _mark_and_push_closure;
+   public:
+    FollowKlassClosure(MarkAndPushClosure* mark_and_push_closure) :
+        _mark_and_push_closure(mark_and_push_closure) { }
+    void do_klass(Klass* klass);
+  };
 };
 
 inline ParCompactionManager* ParCompactionManager::manager_array(int index) {
--- a/hotspot/src/share/vm/gc_implementation/parallelScavenge/psCompactionManager.inline.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/parallelScavenge/psCompactionManager.inline.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -31,6 +31,23 @@
 #include "oops/oop.inline.hpp"
 #include "utilities/debug.hpp"
 #include "utilities/globalDefinitions.hpp"
+#include "utilities/taskqueue.inline.hpp"
+
+inline bool ParCompactionManager::steal(int queue_num, int* seed, oop& t) {
+  return stack_array()->steal(queue_num, seed, t);
+}
+
+inline bool ParCompactionManager::steal_objarray(int queue_num, int* seed, ObjArrayTask& t) {
+  return _objarray_queues->steal(queue_num, seed, t);
+}
+
+inline bool ParCompactionManager::steal(int queue_num, int* seed, size_t& region) {
+  return region_array()->steal(queue_num, seed, region);
+}
+
+inline void ParCompactionManager::push(oop obj) {
+  _marking_stack.push(obj);
+}
 
 void ParCompactionManager::push_objarray(oop obj, size_t index)
 {
@@ -50,6 +67,47 @@
   region_stack()->push(index);
 }
 
+template <typename T>
+inline void ParCompactionManager::mark_and_push(T* p) {
+  T heap_oop = oopDesc::load_heap_oop(p);
+  if (!oopDesc::is_null(heap_oop)) {
+    oop obj = oopDesc::decode_heap_oop_not_null(heap_oop);
+    assert(ParallelScavengeHeap::heap()->is_in(obj), "should be in heap");
+
+    if (mark_bitmap()->is_unmarked(obj) && PSParallelCompact::mark_obj(obj)) {
+      push(obj);
+    }
+  }
+}
+
+template <typename T>
+inline void ParCompactionManager::MarkAndPushClosure::do_oop_nv(T* p) {
+  _compaction_manager->mark_and_push(p);
+}
+
+inline void ParCompactionManager::MarkAndPushClosure::do_oop(oop* p)       { do_oop_nv(p); }
+inline void ParCompactionManager::MarkAndPushClosure::do_oop(narrowOop* p) { do_oop_nv(p); }
+
+inline void ParCompactionManager::follow_klass(Klass* klass) {
+  oop holder = klass->klass_holder();
+  mark_and_push(&holder);
+}
+
+inline void ParCompactionManager::FollowStackClosure::do_void() {
+  _compaction_manager->follow_marking_stacks();
+}
+
+inline void ParCompactionManager::FollowKlassClosure::do_klass(Klass* klass) {
+  klass->oops_do(_mark_and_push_closure);
+}
+
+inline void ParCompactionManager::follow_class_loader(ClassLoaderData* cld) {
+  MarkAndPushClosure mark_and_push_closure(this);
+  FollowKlassClosure follow_klass_closure(&mark_and_push_closure);
+
+  cld->oops_do(&mark_and_push_closure, &follow_klass_closure, true);
+}
+
 inline void ParCompactionManager::follow_contents(oop obj) {
   assert(PSParallelCompact::mark_bitmap()->is_marked(obj), "should be marked");
   obj->pc_follow_contents(this);
@@ -69,7 +127,7 @@
 
   // Push the non-NULL elements of the next stride on the marking stack.
   for (T* e = beg; e < end; e++) {
-    PSParallelCompact::mark_and_push<T>(cm, e);
+    cm->mark_and_push<T>(e);
   }
 
   if (end_index < len) {
--- a/hotspot/src/share/vm/gc_implementation/parallelScavenge/psParallelCompact.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/parallelScavenge/psParallelCompact.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -108,7 +108,6 @@
 bool      PSParallelCompact::_print_phases = false;
 
 ReferenceProcessor* PSParallelCompact::_ref_processor = NULL;
-Klass*              PSParallelCompact::_updated_int_array_klass_obj = NULL;
 
 double PSParallelCompact::_dwl_mean;
 double PSParallelCompact::_dwl_std_dev;
@@ -820,17 +819,9 @@
 
 bool PSParallelCompact::IsAliveClosure::do_object_b(oop p) { return mark_bitmap()->is_marked(p); }
 
-void PSParallelCompact::KeepAliveClosure::do_oop(oop* p)       { PSParallelCompact::KeepAliveClosure::do_oop_work(p); }
-void PSParallelCompact::KeepAliveClosure::do_oop(narrowOop* p) { PSParallelCompact::KeepAliveClosure::do_oop_work(p); }
-
 PSParallelCompact::AdjustPointerClosure PSParallelCompact::_adjust_pointer_closure;
 PSParallelCompact::AdjustKlassClosure PSParallelCompact::_adjust_klass_closure;
 
-void PSParallelCompact::FollowStackClosure::do_void() { _compaction_manager->follow_marking_stacks(); }
-
-void PSParallelCompact::FollowKlassClosure::do_klass(Klass* klass) {
-  klass->oops_do(_mark_and_push_closure);
-}
 void PSParallelCompact::AdjustKlassClosure::do_klass(Klass* klass) {
   klass->oops_do(&PSParallelCompact::_adjust_pointer_closure);
 }
@@ -2350,8 +2341,8 @@
   TaskQueueSetSuper* qset = ParCompactionManager::region_array();
   ParallelTaskTerminator terminator(active_gc_threads, qset);
 
-  PSParallelCompact::MarkAndPushClosure mark_and_push_closure(cm);
-  PSParallelCompact::FollowStackClosure follow_stack_closure(cm);
+  ParCompactionManager::MarkAndPushClosure mark_and_push_closure(cm);
+  ParCompactionManager::FollowStackClosure follow_stack_closure(cm);
 
   // Need new claim bits before marking starts.
   ClassLoaderDataGraph::clear_claimed_marks();
@@ -2425,14 +2416,6 @@
   _gc_tracer.report_object_count_after_gc(is_alive_closure());
 }
 
-void PSParallelCompact::follow_class_loader(ParCompactionManager* cm,
-                                            ClassLoaderData* cld) {
-  PSParallelCompact::MarkAndPushClosure mark_and_push_closure(cm);
-  PSParallelCompact::FollowKlassClosure follow_klass_closure(&mark_and_push_closure);
-
-  cld->oops_do(&mark_and_push_closure, &follow_klass_closure, true);
-}
-
 // This should be moved to the shared markSweep code!
 class PSAlwaysTrueClosure: public BoolObjectClosure {
 public:
--- a/hotspot/src/share/vm/gc_implementation/parallelScavenge/psParallelCompact.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/parallelScavenge/psParallelCompact.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -28,7 +28,6 @@
 #include "gc_implementation/parallelScavenge/objectStartArray.hpp"
 #include "gc_implementation/parallelScavenge/parallelScavengeHeap.hpp"
 #include "gc_implementation/parallelScavenge/parMarkBitMap.hpp"
-#include "gc_implementation/parallelScavenge/psCompactionManager.hpp"
 #include "gc_implementation/shared/collectorCounters.hpp"
 #include "gc_implementation/shared/mutableSpace.hpp"
 #include "gc_interface/collectedHeap.hpp"
@@ -933,25 +932,6 @@
     virtual bool do_object_b(oop p);
   };
 
-  class KeepAliveClosure: public OopClosure {
-   private:
-    ParCompactionManager* _compaction_manager;
-   protected:
-    template <class T> inline void do_oop_work(T* p);
-   public:
-    KeepAliveClosure(ParCompactionManager* cm) : _compaction_manager(cm) { }
-    virtual void do_oop(oop* p);
-    virtual void do_oop(narrowOop* p);
-  };
-
-  class FollowStackClosure: public VoidClosure {
-   private:
-    ParCompactionManager* _compaction_manager;
-   public:
-    FollowStackClosure(ParCompactionManager* cm) : _compaction_manager(cm) { }
-    virtual void do_void();
-  };
-
   class AdjustPointerClosure: public ExtendedOopClosure {
    public:
     template <typename T> void do_oop_nv(T* p);
@@ -967,12 +947,8 @@
     void do_klass(Klass* klass);
   };
 
-  friend class KeepAliveClosure;
-  friend class FollowStackClosure;
   friend class AdjustPointerClosure;
   friend class AdjustKlassClosure;
-  friend class FollowKlassClosure;
-  friend class InstanceClassLoaderKlass;
   friend class RefProcTaskProxy;
 
  private:
@@ -994,9 +970,6 @@
   // Reference processing (used in ...follow_contents)
   static ReferenceProcessor*  _ref_processor;
 
-  // Updated location of intArrayKlassObj.
-  static Klass* _updated_int_array_klass_obj;
-
   // Values computed at initialization and used by dead_wood_limiter().
   static double _dwl_mean;
   static double _dwl_std_dev;
@@ -1142,30 +1115,6 @@
   static void reset_millis_since_last_gc();
 
  public:
-  class MarkAndPushClosure: public ExtendedOopClosure {
-   private:
-    ParCompactionManager* _compaction_manager;
-   public:
-    MarkAndPushClosure(ParCompactionManager* cm) : _compaction_manager(cm) { }
-
-    template <typename T> void do_oop_nv(T* p);
-    virtual void do_oop(oop* p);
-    virtual void do_oop(narrowOop* p);
-
-    // This closure provides its own oop verification code.
-    debug_only(virtual bool should_verify_oops() { return false; })
-  };
-
-  // The one and only place to start following the classes.
-  // Should only be applied to the ClassLoaderData klasses list.
-  class FollowKlassClosure : public KlassClosure {
-   private:
-    MarkAndPushClosure* _mark_and_push_closure;
-   public:
-    FollowKlassClosure(MarkAndPushClosure* mark_and_push_closure) :
-        _mark_and_push_closure(mark_and_push_closure) { }
-    void do_klass(Klass* klass);
-  };
 
   PSParallelCompact();
 
@@ -1193,23 +1142,13 @@
 
   // Used to add tasks
   static GCTaskManager* const gc_task_manager();
-  static Klass* updated_int_array_klass_obj() {
-    return _updated_int_array_klass_obj;
-  }
 
   // Marking support
   static inline bool mark_obj(oop obj);
   static inline bool is_marked(oop obj);
-  // Check mark and maybe push on marking stack
-  template <class T> static inline void mark_and_push(ParCompactionManager* cm,
-                                                      T* p);
+
   template <class T> static inline void adjust_pointer(T* p);
 
-  static inline void follow_klass(ParCompactionManager* cm, Klass* klass);
-
-  static void follow_class_loader(ParCompactionManager* cm,
-                                  ClassLoaderData* klass);
-
   // Compaction support.
   // Return true if p is in the range [beg_addr, end_addr).
   static inline bool is_in(HeapWord* p, HeapWord* beg_addr, HeapWord* end_addr);
@@ -1337,11 +1276,6 @@
   return mark_bitmap()->is_marked(obj);
 }
 
-template <class T>
-inline void PSParallelCompact::KeepAliveClosure::do_oop_work(T* p) {
-  mark_and_push(_compaction_manager, p);
-}
-
 inline bool PSParallelCompact::print_phases() {
   return _print_phases;
 }
--- a/hotspot/src/share/vm/gc_implementation/parallelScavenge/psParallelCompact.inline.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/parallelScavenge/psParallelCompact.inline.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -26,38 +26,11 @@
 #define SHARE_VM_GC_IMPLEMENTATION_PARALLELSCAVENGE_PSPARALLELCOMPACT_INLINE_HPP
 
 #include "gc_implementation/parallelScavenge/parallelScavengeHeap.hpp"
-#include "gc_implementation/parallelScavenge/psCompactionManager.hpp"
 #include "gc_implementation/parallelScavenge/psParallelCompact.hpp"
 #include "gc_interface/collectedHeap.hpp"
 #include "oops/klass.hpp"
 #include "oops/oop.inline.hpp"
 
-template <typename T>
-inline void PSParallelCompact::mark_and_push(ParCompactionManager* cm, T* p) {
-  T heap_oop = oopDesc::load_heap_oop(p);
-  if (!oopDesc::is_null(heap_oop)) {
-    oop obj = oopDesc::decode_heap_oop_not_null(heap_oop);
-    assert(ParallelScavengeHeap::heap()->is_in(obj), "should be in heap");
-
-    if (mark_bitmap()->is_unmarked(obj) && mark_obj(obj)) {
-      cm->push(obj);
-    }
-  }
-}
-
-template <typename T>
-inline void PSParallelCompact::MarkAndPushClosure::do_oop_nv(T* p) {
-  mark_and_push(_compaction_manager, p);
-}
-
-inline void PSParallelCompact::MarkAndPushClosure::do_oop(oop* p)       { do_oop_nv(p); }
-inline void PSParallelCompact::MarkAndPushClosure::do_oop(narrowOop* p) { do_oop_nv(p); }
-
-inline void PSParallelCompact::follow_klass(ParCompactionManager* cm, Klass* klass) {
-  oop holder = klass->klass_holder();
-  mark_and_push(cm, &holder);
-}
-
 template <class T>
 inline void PSParallelCompact::adjust_pointer(T* p) {
   T heap_oop = oopDesc::load_heap_oop(p);
--- a/hotspot/src/share/vm/gc_implementation/parallelScavenge/psPromotionManager.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/parallelScavenge/psPromotionManager.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -36,7 +36,7 @@
 #include "oops/instanceMirrorKlass.inline.hpp"
 #include "oops/objArrayKlass.inline.hpp"
 #include "oops/oop.inline.hpp"
-#include "utilities/stack.inline.hpp"
+#include "utilities/taskqueue.inline.hpp"
 
 PaddedEnd<PSPromotionManager>* PSPromotionManager::_manager_array = NULL;
 OopStarTaskQueueSet*           PSPromotionManager::_stack_array_depth = NULL;
@@ -365,33 +365,19 @@
   // Treat discovered as normal oop, if ref is not "active",
   // i.e. if next is non-NULL.
   T* next_addr = (T*)java_lang_ref_Reference::next_addr(obj);
-  if (ReferenceProcessor::pending_list_uses_discovered_field()) {
-    T  next_oop = oopDesc::load_heap_oop(next_addr);
-    if (!oopDesc::is_null(next_oop)) { // i.e. ref is not "active"
-      T* discovered_addr = (T*)java_lang_ref_Reference::discovered_addr(obj);
-      debug_only(
-        if(TraceReferenceGC && PrintGCDetails) {
-          gclog_or_tty->print_cr("   Process discovered as normal "
-                                 PTR_FORMAT, p2i(discovered_addr));
-        }
-      )
-      if (PSScavenge::should_scavenge(discovered_addr)) {
-        pm->claim_or_forward_depth(discovered_addr);
+  T  next_oop = oopDesc::load_heap_oop(next_addr);
+  if (!oopDesc::is_null(next_oop)) { // i.e. ref is not "active"
+    T* discovered_addr = (T*)java_lang_ref_Reference::discovered_addr(obj);
+    debug_only(
+      if(TraceReferenceGC && PrintGCDetails) {
+        gclog_or_tty->print_cr("   Process discovered as normal "
+                               PTR_FORMAT, p2i(discovered_addr));
       }
+    )
+    if (PSScavenge::should_scavenge(discovered_addr)) {
+      pm->claim_or_forward_depth(discovered_addr);
     }
-  } else {
-#ifdef ASSERT
-    // In the case of older JDKs which do not use the discovered
-    // field for the pending list, an inactive ref (next != NULL)
-    // must always have a NULL discovered field.
-    oop next = oopDesc::load_decode_heap_oop(next_addr);
-    oop discovered = java_lang_ref_Reference::discovered(obj);
-    assert(oopDesc::is_null(next) || oopDesc::is_null(discovered),
-           err_msg("Found an inactive reference " PTR_FORMAT " with a non-NULL discovered field",
-                   p2i(obj)));
-#endif
   }
-
   // Treat next as normal oop;  next is a link in the reference queue.
   if (PSScavenge::should_scavenge(next_addr)) {
     pm->claim_or_forward_depth(next_addr);
--- a/hotspot/src/share/vm/gc_implementation/parallelScavenge/psPromotionManager.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/parallelScavenge/psPromotionManager.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -45,10 +45,6 @@
 // FIX ME FIX ME Add a destructor, and don't rely on the user to drain/flush/deallocate!
 //
 
-// Move to some global location
-#define HAS_BEEN_MOVED 0x1501d01d
-// End move to some global location
-
 class MutableSpace;
 class PSOldGen;
 class ParCompactionManager;
@@ -143,9 +139,7 @@
                                                     int start, int end);
   void process_array_chunk(oop old);
 
-  template <class T> void push_depth(T* p) {
-    claimed_stack_depth()->push(p);
-  }
+  template <class T> void push_depth(T* p);
 
   inline void promotion_trace_event(oop new_obj, oop old_obj, size_t obj_size,
                                     uint age, bool tenured,
@@ -163,9 +157,7 @@
   static PSPromotionManager* gc_thread_promotion_manager(int index);
   static PSPromotionManager* vm_thread_promotion_manager();
 
-  static bool steal_depth(int queue_num, int* seed, StarTask& t) {
-    return stack_array_depth()->steal(queue_num, seed, t);
-  }
+  static bool steal_depth(int queue_num, int* seed, StarTask& t);
 
   PSPromotionManager();
 
--- a/hotspot/src/share/vm/gc_implementation/parallelScavenge/psPromotionManager.inline.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/parallelScavenge/psPromotionManager.inline.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -31,6 +31,7 @@
 #include "gc_implementation/parallelScavenge/psPromotionLAB.inline.hpp"
 #include "gc_implementation/parallelScavenge/psScavenge.hpp"
 #include "oops/oop.inline.hpp"
+#include "utilities/taskqueue.inline.hpp"
 
 inline PSPromotionManager* PSPromotionManager::manager_array(int index) {
   assert(_manager_array != NULL, "access of NULL manager_array");
@@ -39,6 +40,11 @@
 }
 
 template <class T>
+inline void PSPromotionManager::push_depth(T* p) {
+  claimed_stack_depth()->push(p);
+}
+
+template <class T>
 inline void PSPromotionManager::claim_or_forward_internal_depth(T* p) {
   if (p != NULL) { // XXX: error if p != NULL here
     oop o = oopDesc::load_decode_heap_oop_not_null(p);
@@ -99,7 +105,7 @@
 // performance.
 //
 template<bool promote_immediately>
-oop PSPromotionManager::copy_to_survivor_space(oop o) {
+inline oop PSPromotionManager::copy_to_survivor_space(oop o) {
   assert(should_scavenge(&o), "Sanity");
 
   oop new_obj = NULL;
@@ -317,6 +323,10 @@
   }
 }
 
+inline bool PSPromotionManager::steal_depth(int queue_num, int* seed, StarTask& t) {
+  return stack_array_depth()->steal(queue_num, seed, t);
+}
+
 #if TASKQUEUE_STATS
 void PSPromotionManager::record_steal(StarTask& p) {
   if (is_oop_masked(p)) {
--- a/hotspot/src/share/vm/gc_implementation/parallelScavenge/psTasks.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/parallelScavenge/psTasks.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -39,8 +39,7 @@
 #include "runtime/thread.hpp"
 #include "runtime/vmThread.hpp"
 #include "services/management.hpp"
-#include "utilities/stack.inline.hpp"
-#include "utilities/taskqueue.hpp"
+#include "utilities/taskqueue.inline.hpp"
 
 //
 // ScavengeRootsTask
--- a/hotspot/src/share/vm/gc_implementation/shared/adaptiveSizePolicy.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/shared/adaptiveSizePolicy.cpp	Wed Jul 05 20:35:10 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
@@ -97,10 +97,10 @@
 //    Calculate the number of GC threads based on the size of the heap.
 //    Use the larger.
 
-int AdaptiveSizePolicy::calc_default_active_workers(uintx total_workers,
-                                            const uintx min_workers,
-                                            uintx active_workers,
-                                            uintx application_workers) {
+uint AdaptiveSizePolicy::calc_default_active_workers(uintx total_workers,
+                                                     const uintx min_workers,
+                                                     uintx active_workers,
+                                                     uintx application_workers) {
   // If the user has specifically set the number of
   // GC threads, use them.
 
@@ -178,9 +178,9 @@
   return new_active_workers;
 }
 
-int AdaptiveSizePolicy::calc_active_workers(uintx total_workers,
-                                            uintx active_workers,
-                                            uintx application_workers) {
+uint AdaptiveSizePolicy::calc_active_workers(uintx total_workers,
+                                             uintx active_workers,
+                                             uintx application_workers) {
   // If the user has specifically set the number of
   // GC threads, use them.
 
@@ -188,13 +188,14 @@
   // or the users has requested a specific number, set the active
   // number of workers to all the workers.
 
-  int new_active_workers;
+  uint new_active_workers;
   if (!UseDynamicNumberOfGCThreads ||
      (!FLAG_IS_DEFAULT(ParallelGCThreads) && !ForceDynamicNumberOfGCThreads)) {
     new_active_workers = total_workers;
   } else {
+    uintx min_workers = (total_workers == 1) ? 1 : 2;
     new_active_workers = calc_default_active_workers(total_workers,
-                                                     2, /* Minimum number of workers */
+                                                     min_workers,
                                                      active_workers,
                                                      application_workers);
   }
@@ -202,18 +203,17 @@
   return new_active_workers;
 }
 
-int AdaptiveSizePolicy::calc_active_conc_workers(uintx total_workers,
-                                                 uintx active_workers,
-                                                 uintx application_workers) {
+uint AdaptiveSizePolicy::calc_active_conc_workers(uintx total_workers,
+                                                  uintx active_workers,
+                                                  uintx application_workers) {
   if (!UseDynamicNumberOfGCThreads ||
      (!FLAG_IS_DEFAULT(ConcGCThreads) && !ForceDynamicNumberOfGCThreads)) {
     return ConcGCThreads;
   } else {
-    int no_of_gc_threads = calc_default_active_workers(
-                             total_workers,
-                             1, /* Minimum number of workers */
-                             active_workers,
-                             application_workers);
+    uint no_of_gc_threads = calc_default_active_workers(total_workers,
+                                                        1, /* Minimum number of workers */
+                                                        active_workers,
+                                                        application_workers);
     return no_of_gc_threads;
   }
 }
--- a/hotspot/src/share/vm/gc_implementation/shared/adaptiveSizePolicy.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/shared/adaptiveSizePolicy.hpp	Wed Jul 05 20:35:10 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
@@ -343,10 +343,10 @@
                      uint gc_cost_ratio);
 
   // Return number default  GC threads to use in the next GC.
-  static int calc_default_active_workers(uintx total_workers,
-                                         const uintx min_workers,
-                                         uintx active_workers,
-                                         uintx application_workers);
+  static uint calc_default_active_workers(uintx total_workers,
+                                          const uintx min_workers,
+                                          uintx active_workers,
+                                          uintx application_workers);
 
   // Return number of GC threads to use in the next GC.
   // This is called sparingly so as not to change the
@@ -358,14 +358,14 @@
   // GC workers from the calls above.  For example,
   // a CMS parallel remark uses the same number of GC
   // workers as the most recent ParNew collection.
-  static int calc_active_workers(uintx total_workers,
-                                 uintx active_workers,
-                                 uintx application_workers);
+  static uint calc_active_workers(uintx total_workers,
+                                  uintx active_workers,
+                                  uintx application_workers);
 
   // Return number of GC threads to use in the next concurrent GC phase.
-  static int calc_active_conc_workers(uintx total_workers,
-                                      uintx active_workers,
-                                      uintx application_workers);
+  static uint calc_active_conc_workers(uintx total_workers,
+                                       uintx active_workers,
+                                       uintx application_workers);
 
   bool is_gc_cms_adaptive_size_policy() {
     return kind() == _gc_cms_adaptive_size_policy;
--- a/hotspot/src/share/vm/gc_implementation/shared/markSweep.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/shared/markSweep.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -145,31 +145,18 @@
     }
   }
   T* next_addr = (T*)java_lang_ref_Reference::next_addr(obj);
-  if (ReferenceProcessor::pending_list_uses_discovered_field()) {
-    // Treat discovered as normal oop, if ref is not "active",
-    // i.e. if next is non-NULL.
-    T  next_oop = oopDesc::load_heap_oop(next_addr);
-    if (!oopDesc::is_null(next_oop)) { // i.e. ref is not "active"
-      T* discovered_addr = (T*)java_lang_ref_Reference::discovered_addr(obj);
-      debug_only(
-        if(TraceReferenceGC && PrintGCDetails) {
-          gclog_or_tty->print_cr("   Process discovered as normal "
-                                 PTR_FORMAT, p2i(discovered_addr));
-        }
-      )
-      MarkSweep::mark_and_push(discovered_addr);
-    }
-  } else {
-#ifdef ASSERT
-    // In the case of older JDKs which do not use the discovered
-    // field for the pending list, an inactive ref (next != NULL)
-    // must always have a NULL discovered field.
-    oop next = oopDesc::load_decode_heap_oop(next_addr);
-    oop discovered = java_lang_ref_Reference::discovered(obj);
-    assert(oopDesc::is_null(next) || oopDesc::is_null(discovered),
-        err_msg("Found an inactive reference " PTR_FORMAT " with a non-NULL discovered field",
-            p2i(obj)));
-#endif
+  // Treat discovered as normal oop, if ref is not "active",
+  // i.e. if next is non-NULL.
+  T  next_oop = oopDesc::load_heap_oop(next_addr);
+  if (!oopDesc::is_null(next_oop)) { // i.e. ref is not "active"
+    T* discovered_addr = (T*)java_lang_ref_Reference::discovered_addr(obj);
+    debug_only(
+      if(TraceReferenceGC && PrintGCDetails) {
+        gclog_or_tty->print_cr("   Process discovered as normal "
+                               PTR_FORMAT, p2i(discovered_addr));
+      }
+    )
+    MarkSweep::mark_and_push(discovered_addr);
   }
   // treat next as normal oop.  next is a link in the reference queue.
   debug_only(
--- a/hotspot/src/share/vm/gc_implementation/shared/objectCountEventSender.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/shared/objectCountEventSender.hpp	Wed Jul 05 20:35:10 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
@@ -22,8 +22,8 @@
  *
  */
 
-#ifndef SHARE_VM_OBJECT_COUNT_EVENT_SENDER_HPP
-#define SHARE_VM_OBJECT_COUNT_EVENT_SENDER_HPP
+#ifndef SHARE_VM_GC_IMPLEMENTATION_SHARED_OBJECTCOUNTEVENTSENDER_HPP
+#define SHARE_VM_GC_IMPLEMENTATION_SHARED_OBJECTCOUNTEVENTSENDER_HPP
 
 #include "gc_implementation/shared/gcTrace.hpp"
 #include "memory/allocation.hpp"
@@ -42,4 +42,4 @@
 
 #endif // INCLUDE_SERVICES
 
-#endif // SHARE_VM_OBJECT_COUNT_EVENT_SENDER
+#endif // SHARE_VM_GC_IMPLEMENTATION_SHARED_OBJECTCOUNTEVENTSENDER_HPP
--- a/hotspot/src/share/vm/gc_implementation/shared/plab.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/shared/plab.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -24,6 +24,7 @@
 
 #include "precompiled.hpp"
 #include "gc_implementation/shared/plab.hpp"
+#include "gc_interface/collectedHeap.hpp"
 #include "memory/threadLocalAllocBuffer.hpp"
 #include "oops/arrayOop.hpp"
 #include "oops/oop.inline.hpp"
@@ -39,7 +40,7 @@
 
 PLAB::PLAB(size_t desired_plab_sz_) :
   _word_sz(desired_plab_sz_), _bottom(NULL), _top(NULL),
-  _end(NULL), _hard_end(NULL), _allocated(0), _wasted(0)
+  _end(NULL), _hard_end(NULL), _allocated(0), _wasted(0), _undo_wasted(0)
 {
   // ArrayOopDesc::header_size depends on command line initialization.
   AlignmentReserve = oopDesc::header_size() > MinObjAlignment ? align_object_size(arrayOopDesc::header_size(T_INT)) : 0;
@@ -62,13 +63,15 @@
   // Now flush the statistics.
   stats->add_allocated(_allocated);
   stats->add_wasted(_wasted);
+  stats->add_undo_wasted(_undo_wasted);
   stats->add_unused(unused);
 
   // Since we have flushed the stats we need to clear  the _allocated and _wasted
   // fields in case somebody retains an instance of this over GCs. Not doing so
   // will artifically inflate the values in the statistics.
-  _allocated = 0;
-  _wasted = 0;
+  _allocated   = 0;
+  _wasted      = 0;
+  _undo_wasted = 0;
 }
 
 void PLAB::retire() {
@@ -84,6 +87,28 @@
   return result;
 }
 
+void PLAB::add_undo_waste(HeapWord* obj, size_t word_sz) {
+  CollectedHeap::fill_with_object(obj, word_sz);
+  _undo_wasted += word_sz;
+}
+
+void PLAB::undo_last_allocation(HeapWord* obj, size_t word_sz) {
+  assert(pointer_delta(_top, _bottom) >= word_sz, "Bad undo");
+  assert(pointer_delta(_top, obj) == word_sz, "Bad undo");
+  _top = obj;
+}
+
+void PLAB::undo_allocation(HeapWord* obj, size_t word_sz) {
+  // Is the alloc in the current alloc buffer?
+  if (contains(obj)) {
+    assert(contains(obj + word_sz - 1),
+      "should contain whole object");
+    undo_last_allocation(obj, word_sz);
+  } else {
+    add_undo_waste(obj, word_sz);
+  }
+}
+
 // Compute desired plab size and latch result for later
 // use. This should be called once at the end of parallel
 // scavenge; it clears the sensor accumulators.
@@ -98,8 +123,9 @@
            err_msg("Inconsistency in PLAB stats: "
                    "_allocated: "SIZE_FORMAT", "
                    "_wasted: "SIZE_FORMAT", "
-                   "_unused: "SIZE_FORMAT,
-                   _allocated, _wasted, _unused));
+                   "_unused: "SIZE_FORMAT", "
+                   "_undo_wasted: "SIZE_FORMAT,
+                   _allocated, _wasted, _unused, _undo_wasted));
 
     _allocated = 1;
   }
--- a/hotspot/src/share/vm/gc_implementation/shared/plab.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/shared/plab.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -45,6 +45,7 @@
   // In support of ergonomic sizing of PLAB's
   size_t    _allocated;     // in HeapWord units
   size_t    _wasted;        // in HeapWord units
+  size_t    _undo_wasted;
   char      tail[32];
   static size_t AlignmentReserve;
 
@@ -62,6 +63,12 @@
   // the amount of remaining space.
   size_t retire_internal();
 
+  void add_undo_waste(HeapWord* obj, size_t word_sz);
+
+  // Undo the last allocation in the buffer, which is required to be of the
+  // "obj" of the given "word_sz".
+  void undo_last_allocation(HeapWord* obj, size_t word_sz);
+
 public:
   // Initializes the buffer to be empty, but with the given "word_sz".
   // Must get initialized with "set_buf" for an allocation to succeed.
@@ -90,18 +97,17 @@
   // Allocate the object aligned to "alignment_in_bytes".
   HeapWord* allocate_aligned(size_t word_sz, unsigned short alignment_in_bytes);
 
-  // Undo the last allocation in the buffer, which is required to be of the
+  // Undo any allocation in the buffer, which is required to be of the
   // "obj" of the given "word_sz".
-  void undo_allocation(HeapWord* obj, size_t word_sz) {
-    assert(pointer_delta(_top, _bottom) >= word_sz, "Bad undo");
-    assert(pointer_delta(_top, obj)     == word_sz, "Bad undo");
-    _top = obj;
-  }
+  void undo_allocation(HeapWord* obj, size_t word_sz);
 
   // The total (word) size of the buffer, including both allocated and
   // unallocated space.
   size_t word_sz() { return _word_sz; }
 
+  size_t waste() { return _wasted; }
+  size_t undo_waste() { return _undo_wasted; }
+
   // Should only be done if we are about to reset with a new buffer of the
   // given size.
   void set_word_size(size_t new_word_sz) {
@@ -146,20 +152,23 @@
 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
   AdaptiveWeightedAverage
          _filter;         // Integrator with decay
 
   void reset() {
-    _allocated = 0;
-    _wasted    = 0;
-    _unused    = 0;
+    _allocated   = 0;
+    _wasted      = 0;
+    _undo_wasted = 0;
+    _unused      = 0;
   }
  public:
   PLABStats(size_t desired_plab_sz_, unsigned wt) :
     _allocated(0),
     _wasted(0),
+    _undo_wasted(0),
     _unused(0),
     _desired_plab_sz(desired_plab_sz_),
     _filter(wt)
@@ -192,6 +201,10 @@
   void add_wasted(size_t v) {
     Atomic::add_ptr(v, &_wasted);
   }
+
+  void add_undo_wasted(size_t v) {
+    Atomic::add_ptr(v, &_undo_wasted);
+  }
 };
 
 #endif // SHARE_VM_GC_IMPLEMENTATION_SHARED_PLAB_HPP
--- a/hotspot/src/share/vm/gc_implementation/shared/suspendibleThreadSet.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/shared/suspendibleThreadSet.cpp	Wed Jul 05 20:35:10 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
@@ -33,16 +33,20 @@
 double SuspendibleThreadSet::_suspend_all_start = 0.0;
 
 void SuspendibleThreadSet::join() {
+  assert(!Thread::current()->is_suspendible_thread(), "Thread already joined");
   MonitorLockerEx ml(STS_lock, Mutex::_no_safepoint_check_flag);
   while (_suspend_all) {
     ml.wait(Mutex::_no_safepoint_check_flag);
   }
   _nthreads++;
+  DEBUG_ONLY(Thread::current()->set_suspendible_thread();)
 }
 
 void SuspendibleThreadSet::leave() {
+  assert(Thread::current()->is_suspendible_thread(), "Thread not joined");
   MonitorLockerEx ml(STS_lock, Mutex::_no_safepoint_check_flag);
   assert(_nthreads > 0, "Invalid");
+  DEBUG_ONLY(Thread::current()->clear_suspendible_thread();)
   _nthreads--;
   if (_suspend_all) {
     ml.notify_all();
@@ -50,6 +54,7 @@
 }
 
 void SuspendibleThreadSet::yield() {
+  assert(Thread::current()->is_suspendible_thread(), "Must have joined");
   if (_suspend_all) {
     MonitorLockerEx ml(STS_lock, Mutex::_no_safepoint_check_flag);
     if (_suspend_all) {
--- a/hotspot/src/share/vm/gc_implementation/shared/suspendibleThreadSet.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_implementation/shared/suspendibleThreadSet.hpp	Wed Jul 05 20:35:10 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
@@ -36,19 +36,22 @@
 // suspending thread later calls desynchronize(), allowing the suspended
 // threads to continue.
 class SuspendibleThreadSet : public AllStatic {
+  friend class SuspendibleThreadSetJoiner;
+  friend class SuspendibleThreadSetLeaver;
+
 private:
   static uint   _nthreads;
   static uint   _nthreads_stopped;
   static bool   _suspend_all;
   static double _suspend_all_start;
 
-public:
   // Add the current thread to the set. May block if a suspension is in progress.
   static void join();
 
   // Removes the current thread from the set.
   static void leave();
 
+public:
   // Returns true if an suspension is in progress.
   static bool should_yield() { return _suspend_all; }
 
@@ -63,22 +66,52 @@
 };
 
 class SuspendibleThreadSetJoiner : public StackObj {
+private:
+  bool _active;
+
 public:
-  SuspendibleThreadSetJoiner() {
-    SuspendibleThreadSet::join();
+  SuspendibleThreadSetJoiner(bool active = true) : _active(active) {
+    if (_active) {
+      SuspendibleThreadSet::join();
+    }
   }
 
   ~SuspendibleThreadSetJoiner() {
-    SuspendibleThreadSet::leave();
+    if (_active) {
+      SuspendibleThreadSet::leave();
+    }
   }
 
   bool should_yield() {
-    return SuspendibleThreadSet::should_yield();
+    if (_active) {
+      return SuspendibleThreadSet::should_yield();
+    } else {
+      return false;
+    }
   }
 
   void yield() {
+    assert(_active, "Thread has not joined the suspendible thread set");
     SuspendibleThreadSet::yield();
   }
 };
 
+class SuspendibleThreadSetLeaver : public StackObj {
+private:
+  bool _active;
+
+public:
+  SuspendibleThreadSetLeaver(bool active = true) : _active(active) {
+    if (_active) {
+      SuspendibleThreadSet::leave();
+    }
+  }
+
+  ~SuspendibleThreadSetLeaver() {
+    if (_active) {
+      SuspendibleThreadSet::join();
+    }
+  }
+};
+
 #endif // SHARE_VM_GC_IMPLEMENTATION_SHARED_SUSPENDIBLETHREADSET_HPP
--- a/hotspot/src/share/vm/gc_interface/collectedHeap.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/gc_interface/collectedHeap.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -598,13 +598,6 @@
 #endif
 
  public:
-  // This is a convenience method that is used in cases where
-  // the actual number of GC worker threads is not pertinent but
-  // only whether there more than 0.  Use of this method helps
-  // reduce the occurrence of ParallelGCThreads to uses where the
-  // actual number may be germane.
-  static bool use_parallel_gc_threads() { return ParallelGCThreads > 0; }
-
   // Copy the current allocation context statistics for the specified contexts.
   // For each context in contexts, set the corresponding entries in the totals
   // and accuracy arrays to the current values held by the statistics.  Each
--- a/hotspot/src/share/vm/interpreter/cppInterpreterGenerator.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/interpreter/cppInterpreterGenerator.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -29,6 +29,10 @@
 // of the template interpreter generator.
 
 #ifdef CC_INTERP
+#ifdef TARGET_ARCH_zero
+# include "entry_zero.hpp"
+# include "interpreter/interp_masm.hpp"
+#endif
 
 class CppInterpreterGenerator: public AbstractInterpreterGenerator {
   protected:
--- a/hotspot/src/share/vm/interpreter/interpreter.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/interpreter/interpreter.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -29,11 +29,9 @@
 #include "interpreter/cppInterpreter.hpp"
 #include "interpreter/templateInterpreter.hpp"
 #include "memory/resourceArea.hpp"
-#ifdef ZERO
 #ifdef TARGET_ARCH_zero
 # include "entry_zero.hpp"
 #endif
-#endif
 
 // This file contains the platform-independent parts
 // of the interpreter and the interpreter generator.
--- a/hotspot/src/share/vm/interpreter/interpreterGenerator.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/interpreter/interpreterGenerator.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -27,6 +27,7 @@
 
 #include "interpreter/cppInterpreter.hpp"
 #include "interpreter/cppInterpreterGenerator.hpp"
+#include "interpreter/interp_masm.hpp"
 #include "interpreter/templateInterpreter.hpp"
 #include "interpreter/templateInterpreterGenerator.hpp"
 
--- a/hotspot/src/share/vm/interpreter/interpreterRuntime.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/interpreter/interpreterRuntime.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1326,6 +1326,8 @@
       member_name_oop = java_lang_invoke_DirectMethodHandle::member(member_name_oop);
     }
     thread->set_vm_result(member_name_oop);
+  } else {
+    thread->set_vm_result(NULL);
   }
 IRT_END
 #endif // INCLUDE_JVMTI
--- a/hotspot/src/share/vm/memory/genCollectedHeap.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/memory/genCollectedHeap.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -640,7 +640,7 @@
   // All threads execute the following. A specific chunk of buckets
   // from the StringTable are the individual tasks.
   if (weak_roots != NULL) {
-    if (CollectedHeap::use_parallel_gc_threads()) {
+    if (is_par) {
       StringTable::possibly_parallel_oops_do(weak_roots);
     } else {
       StringTable::oops_do(weak_roots);
--- a/hotspot/src/share/vm/memory/guardedMemory.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/memory/guardedMemory.hpp	Wed Jul 05 20:35:10 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
@@ -22,8 +22,8 @@
  *
  */
 
-#ifndef SHARE_VM_MEMORY_GUARDED_MEMORY_HPP
-#define SHARE_VM_MEMORY_GUARDED_MEMORY_HPP
+#ifndef SHARE_VM_MEMORY_GUARDEDMEMORY_HPP
+#define SHARE_VM_MEMORY_GUARDEDMEMORY_HPP
 
 #include "memory/allocation.hpp"
 #include "utilities/globalDefinitions.hpp"
@@ -323,4 +323,4 @@
 #endif
 }; // GuardedMemory
 
-#endif // SHARE_VM_MEMORY_GUARDED_MEMORY_HPP
+#endif // SHARE_VM_MEMORY_GUARDEDMEMORY_HPP
--- a/hotspot/src/share/vm/memory/metaspace.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/memory/metaspace.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -252,7 +252,7 @@
 // Used to manage the free list of Metablocks (a block corresponds
 // to the allocation of a quantum of metadata).
 class BlockFreelist VALUE_OBJ_CLASS_SPEC {
-  BlockTreeDictionary* _dictionary;
+  BlockTreeDictionary* const _dictionary;
 
   // Only allocate and split from freelist if the size of the allocation
   // is at least 1/4th the size of the available block.
@@ -269,13 +269,7 @@
   MetaWord* get_block(size_t word_size);
   void return_block(MetaWord* p, size_t word_size);
 
-  size_t total_size() {
-  if (dictionary() == NULL) {
-    return 0;
-  } else {
-    return dictionary()->total_size();
-  }
-}
+  size_t total_size() { return dictionary()->total_size(); }
 
   void print_on(outputStream* st) const;
 };
@@ -814,30 +808,21 @@
 
 // BlockFreelist methods
 
-BlockFreelist::BlockFreelist() : _dictionary(NULL) {}
+BlockFreelist::BlockFreelist() : _dictionary(new BlockTreeDictionary()) {}
 
 BlockFreelist::~BlockFreelist() {
-  if (_dictionary != NULL) {
-    if (Verbose && TraceMetadataChunkAllocation) {
-      _dictionary->print_free_lists(gclog_or_tty);
-    }
-    delete _dictionary;
+  if (Verbose && TraceMetadataChunkAllocation) {
+    dictionary()->print_free_lists(gclog_or_tty);
   }
+  delete _dictionary;
 }
 
 void BlockFreelist::return_block(MetaWord* p, size_t word_size) {
   Metablock* free_chunk = ::new (p) Metablock(word_size);
-  if (dictionary() == NULL) {
-   _dictionary = new BlockTreeDictionary();
-  }
   dictionary()->return_chunk(free_chunk);
 }
 
 MetaWord* BlockFreelist::get_block(size_t word_size) {
-  if (dictionary() == NULL) {
-    return NULL;
-  }
-
   if (word_size < TreeChunk<Metablock, FreeList<Metablock> >::min_size()) {
     // Dark matter.  Too small for dictionary.
     return NULL;
@@ -866,9 +851,6 @@
 }
 
 void BlockFreelist::print_on(outputStream* st) const {
-  if (dictionary() == NULL) {
-    return;
-  }
   dictionary()->print_free_lists(st);
 }
 
--- a/hotspot/src/share/vm/memory/metaspaceChunkFreeListSummary.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/memory/metaspaceChunkFreeListSummary.hpp	Wed Jul 05 20:35:10 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
@@ -21,8 +21,9 @@
  * questions.
  *
  */
-#ifndef SHARE_VM_MEMORY_METASPACE_CHUNK_FREE_LIST_SUMMARY_HPP
-#define SHARE_VM_MEMORY_METASPACE_CHUNK_FREE_LIST_SUMMARY_HPP
+
+#ifndef SHARE_VM_MEMORY_METASPACECHUNKFREELISTSUMMARY_HPP
+#define SHARE_VM_MEMORY_METASPACECHUNKFREELISTSUMMARY_HPP
 
 #include "memory/allocation.hpp"
 
@@ -100,4 +101,4 @@
   }
 };
 
-#endif // SHARE_VM_MEMORY_METASPACE_CHUNK_FREE_LIST_SUMMARY_HPP
+#endif // SHARE_VM_MEMORY_METASPACECHUNKFREELISTSUMMARY_HPP
--- a/hotspot/src/share/vm/memory/metaspaceGCThresholdUpdater.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/memory/metaspaceGCThresholdUpdater.hpp	Wed Jul 05 20:35:10 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
@@ -22,8 +22,8 @@
  *
  */
 
-#ifndef SHARE_VM_MEMORY_METASPACE_GC_THRESHOLD_UPDATER_HPP
-#define SHARE_VM_MEMORY_METASPACE_GC_THRESHOLD_UPDATER_HPP
+#ifndef SHARE_VM_MEMORY_METASPACEGCTHRESHOLDUPDATER_HPP
+#define SHARE_VM_MEMORY_METASPACEGCTHRESHOLDUPDATER_HPP
 
 #include "memory/allocation.hpp"
 #include "utilities/debug.hpp"
@@ -49,4 +49,4 @@
   }
 };
 
-#endif // SHARE_VM_MEMORY_METASPACE_GC_THRESHOLD_UPDATER_HPP
+#endif // SHARE_VM_MEMORY_METASPACEGCTHRESHOLDUPDATER_HPP
--- a/hotspot/src/share/vm/memory/metaspaceShared.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/memory/metaspaceShared.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -21,8 +21,9 @@
  * questions.
  *
  */
-#ifndef SHARE_VM_MEMORY_METASPACE_SHARED_HPP
-#define SHARE_VM_MEMORY_METASPACE_SHARED_HPP
+
+#ifndef SHARE_VM_MEMORY_METASPACESHARED_HPP
+#define SHARE_VM_MEMORY_METASPACESHARED_HPP
 
 #include "classfile/compactHashtable.hpp"
 #include "memory/allocation.hpp"
@@ -153,4 +154,4 @@
   static int count_class(const char* classlist_file);
   static void estimate_regions_size() NOT_CDS_RETURN;
 };
-#endif // SHARE_VM_MEMORY_METASPACE_SHARED_HPP
+#endif // SHARE_VM_MEMORY_METASPACESHARED_HPP
--- a/hotspot/src/share/vm/memory/metaspaceTracer.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/memory/metaspaceTracer.hpp	Wed Jul 05 20:35:10 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
@@ -22,8 +22,8 @@
  *
  */
 
-#ifndef SHARE_VM_MEMORY_METASPACE_TRACER_HPP
-#define SHARE_VM_MEMORY_METASPACE_TRACER_HPP
+#ifndef SHARE_VM_MEMORY_METASPACETRACER_HPP
+#define SHARE_VM_MEMORY_METASPACETRACER_HPP
 
 #include "memory/allocation.hpp"
 #include "memory/metaspace.hpp"
@@ -52,4 +52,4 @@
 
 };
 
-#endif // SHARE_VM_MEMORY_METASPACE_TRACER_HPP
+#endif // SHARE_VM_MEMORY_METASPACETRACER_HPP
--- a/hotspot/src/share/vm/memory/padded.inline.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/memory/padded.inline.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013, 2014, 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
@@ -22,6 +22,9 @@
  *
  */
 
+#ifndef SHARE_VM_MEMORY_PADDED_INLINE_HPP
+#define SHARE_VM_MEMORY_PADDED_INLINE_HPP
+
 #include "memory/allocation.inline.hpp"
 #include "memory/padded.hpp"
 #include "utilities/debug.hpp"
@@ -86,3 +89,5 @@
 
   return (T*)align_pointer_up(chunk, alignment);
 }
+
+#endif // SHARE_VM_MEMORY_PADDED_INLINE_HPP
--- a/hotspot/src/share/vm/memory/referenceProcessor.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/memory/referenceProcessor.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -37,7 +37,6 @@
 
 ReferencePolicy* ReferenceProcessor::_always_clear_soft_ref_policy = NULL;
 ReferencePolicy* ReferenceProcessor::_default_soft_ref_policy      = NULL;
-bool             ReferenceProcessor::_pending_list_uses_discovered_field = false;
 jlong            ReferenceProcessor::_soft_ref_timestamp_clock = 0;
 
 void referenceProcessor_init() {
@@ -63,7 +62,6 @@
   guarantee(RefDiscoveryPolicy == ReferenceBasedDiscovery ||
             RefDiscoveryPolicy == ReferentBasedDiscovery,
             "Unrecognized RefDiscoveryPolicy");
-  _pending_list_uses_discovered_field = JDK_Version::current().pending_list_uses_discovered_field();
 }
 
 void ReferenceProcessor::enable_discovery(bool check_no_refs) {
@@ -353,10 +351,6 @@
   // all linked Reference objects. Note that it is important to not dirty any
   // cards during reference processing since this will cause card table
   // verification to fail for G1.
-  //
-  // BKWRD COMPATIBILITY NOTE: For older JDKs (prior to the fix for 4956777),
-  // the "next" field is used to chain the pending list, not the discovered
-  // field.
   if (TraceReferenceGC && PrintGCDetails) {
     gclog_or_tty->print_cr("ReferenceProcessor::enqueue_discovered_reflist list "
                            INTPTR_FORMAT, p2i(refs_list.head()));
@@ -364,64 +358,30 @@
 
   oop obj = NULL;
   oop next_d = refs_list.head();
-  if (pending_list_uses_discovered_field()) { // New behavior
-    // Walk down the list, self-looping the next field
-    // so that the References are not considered active.
-    while (obj != next_d) {
-      obj = next_d;
-      assert(obj->is_instanceRef(), "should be reference object");
-      next_d = java_lang_ref_Reference::discovered(obj);
-      if (TraceReferenceGC && PrintGCDetails) {
-        gclog_or_tty->print_cr("        obj " INTPTR_FORMAT "/next_d " INTPTR_FORMAT,
-                               p2i(obj), p2i(next_d));
-      }
-      assert(java_lang_ref_Reference::next(obj) == NULL,
-             "Reference not active; should not be discovered");
-      // Self-loop next, so as to make Ref not active.
-      java_lang_ref_Reference::set_next_raw(obj, obj);
-      if (next_d != obj) {
-        oopDesc::bs()->write_ref_field(java_lang_ref_Reference::discovered_addr(obj), next_d);
-      } else {
-        // This is the last object.
-        // Swap refs_list into pending_list_addr and
-        // set obj's discovered to what we read from pending_list_addr.
-        oop old = oopDesc::atomic_exchange_oop(refs_list.head(), pending_list_addr);
-        // Need post-barrier on pending_list_addr. See enqueue_discovered_ref_helper() above.
-        java_lang_ref_Reference::set_discovered_raw(obj, old); // old may be NULL
-        oopDesc::bs()->write_ref_field(java_lang_ref_Reference::discovered_addr(obj), old);
-      }
+  // Walk down the list, self-looping the next field
+  // so that the References are not considered active.
+  while (obj != next_d) {
+    obj = next_d;
+    assert(obj->is_instanceRef(), "should be reference object");
+    next_d = java_lang_ref_Reference::discovered(obj);
+    if (TraceReferenceGC && PrintGCDetails) {
+      gclog_or_tty->print_cr("        obj " INTPTR_FORMAT "/next_d " INTPTR_FORMAT,
+                             p2i(obj), p2i(next_d));
     }
-  } else { // Old behavior
-    // Walk down the list, copying the discovered field into
-    // the next field and clearing the discovered field.
-    while (obj != next_d) {
-      obj = next_d;
-      assert(obj->is_instanceRef(), "should be reference object");
-      next_d = java_lang_ref_Reference::discovered(obj);
-      if (TraceReferenceGC && PrintGCDetails) {
-        gclog_or_tty->print_cr("        obj " INTPTR_FORMAT "/next_d " INTPTR_FORMAT,
-                               p2i(obj), p2i(next_d));
-      }
-      assert(java_lang_ref_Reference::next(obj) == NULL,
-             "The reference should not be enqueued");
-      if (next_d == obj) {  // obj is last
-        // Swap refs_list into pending_list_addr and
-        // set obj's next to what we read from pending_list_addr.
-        oop old = oopDesc::atomic_exchange_oop(refs_list.head(), pending_list_addr);
-        // Need oop_check on pending_list_addr above;
-        // see special oop-check code at the end of
-        // enqueue_discovered_reflists() further below.
-        if (old == NULL) {
-          // obj should be made to point to itself, since
-          // pending list was empty.
-          java_lang_ref_Reference::set_next(obj, obj);
-        } else {
-          java_lang_ref_Reference::set_next(obj, old);
-        }
-      } else {
-        java_lang_ref_Reference::set_next(obj, next_d);
-      }
-      java_lang_ref_Reference::set_discovered(obj, (oop) NULL);
+    assert(java_lang_ref_Reference::next(obj) == NULL,
+           "Reference not active; should not be discovered");
+    // Self-loop next, so as to make Ref not active.
+    java_lang_ref_Reference::set_next_raw(obj, obj);
+    if (next_d != obj) {
+      oopDesc::bs()->write_ref_field(java_lang_ref_Reference::discovered_addr(obj), next_d);
+    } else {
+      // This is the last object.
+      // Swap refs_list into pending_list_addr and
+      // set obj's discovered to what we read from pending_list_addr.
+      oop old = oopDesc::atomic_exchange_oop(refs_list.head(), pending_list_addr);
+      // Need post-barrier on pending_list_addr. See enqueue_discovered_ref_helper() above.
+      java_lang_ref_Reference::set_discovered_raw(obj, old); // old may be NULL
+      oopDesc::bs()->write_ref_field(java_lang_ref_Reference::discovered_addr(obj), old);
     }
   }
 }
@@ -515,22 +475,6 @@
   _refs_list.dec_length(1);
 }
 
-// Make the Reference object active again.
-void DiscoveredListIterator::make_active() {
-  // The pre barrier for G1 is probably just needed for the old
-  // reference processing behavior. Should we guard this with
-  // ReferenceProcessor::pending_list_uses_discovered_field() ?
-  if (UseG1GC) {
-    HeapWord* next_addr = java_lang_ref_Reference::next_addr(_ref);
-    if (UseCompressedOops) {
-      oopDesc::bs()->write_ref_field_pre((narrowOop*)next_addr, NULL);
-    } else {
-      oopDesc::bs()->write_ref_field_pre((oop*)next_addr, NULL);
-    }
-  }
-  java_lang_ref_Reference::set_next_raw(_ref, NULL);
-}
-
 void DiscoveredListIterator::clear_referent() {
   oop_store_raw(_referent_addr, NULL);
 }
@@ -567,8 +511,6 @@
       }
       // Remove Reference object from list
       iter.remove();
-      // Make the Reference object active again
-      iter.make_active();
       // keep the referent around
       iter.make_referent_alive();
       iter.move_to_next();
--- a/hotspot/src/share/vm/memory/referenceProcessor.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/memory/referenceProcessor.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -161,9 +161,6 @@
   // Remove the current reference from the list
   void remove();
 
-  // Make the Reference object active again.
-  void make_active();
-
   // Make the referent alive.
   inline void make_referent_alive() {
     if (UseCompressedOops) {
@@ -200,9 +197,6 @@
   size_t total_count(DiscoveredList lists[]);
 
  protected:
-  // Compatibility with pre-4965777 JDK's
-  static bool _pending_list_uses_discovered_field;
-
   // The SoftReference master timestamp clock
   static jlong _soft_ref_timestamp_clock;
 
@@ -421,13 +415,6 @@
   bool discovery_is_atomic() const { return _discovery_is_atomic; }
   void set_atomic_discovery(bool atomic) { _discovery_is_atomic = atomic; }
 
-  // whether the JDK in which we are embedded is a pre-4965777 JDK,
-  // and thus whether or not it uses the discovered field to chain
-  // the entries in the pending list.
-  static bool pending_list_uses_discovered_field() {
-    return _pending_list_uses_discovered_field;
-  }
-
   // whether discovery is done by multiple threads same-old-timeously
   bool discovery_is_mt() const { return _discovery_is_mt; }
   void set_mt_discovery(bool mt) { _discovery_is_mt = mt; }
--- a/hotspot/src/share/vm/memory/referenceType.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/memory/referenceType.hpp	Wed Jul 05 20:35:10 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
@@ -22,8 +22,8 @@
  *
  */
 
-#ifndef SHARE_VM_MEMORY_REFRERENCETYPE_HPP
-#define SHARE_VM_MEMORY_REFRERENCETYPE_HPP
+#ifndef SHARE_VM_MEMORY_REFERENCETYPE_HPP
+#define SHARE_VM_MEMORY_REFERENCETYPE_HPP
 
 #include "utilities/debug.hpp"
 
@@ -39,4 +39,4 @@
   REF_CLEANER    // Subclass of sun/misc/Cleaner
 };
 
-#endif // SHARE_VM_MEMORY_REFRERENCETYPE_HPP
+#endif // SHARE_VM_MEMORY_REFERENCETYPE_HPP
--- a/hotspot/src/share/vm/oops/instanceRefKlass.inline.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/oops/instanceRefKlass.inline.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -55,30 +55,17 @@
     }
   }
   T* next_addr = (T*)java_lang_ref_Reference::next_addr(obj);
-  if (ReferenceProcessor::pending_list_uses_discovered_field()) {
-    T next_oop  = oopDesc::load_heap_oop(next_addr);
-    // Treat discovered as normal oop, if ref is not "active" (next non-NULL)
-    if (!oopDesc::is_null(next_oop) && contains(disc_addr)) {
-      // i.e. ref is not "active"
-      debug_only(
-        if(TraceReferenceGC && PrintGCDetails) {
-          gclog_or_tty->print_cr("   Process discovered as normal "
-                                 PTR_FORMAT, p2i(disc_addr));
-        }
-      )
-      Devirtualizer<nv>::do_oop(closure, disc_addr);
-    }
-  } else {
-    // In the case of older JDKs which do not use the discovered field for
-    // the pending list, an inactive ref (next != NULL) must always have a
-    // NULL discovered field.
+  T next_oop  = oopDesc::load_heap_oop(next_addr);
+  // Treat discovered as normal oop, if ref is not "active" (next non-NULL)
+  if (!oopDesc::is_null(next_oop) && contains(disc_addr)) {
+    // i.e. ref is not "active"
     debug_only(
-      T next_oop = oopDesc::load_heap_oop(next_addr);
-      T disc_oop = oopDesc::load_heap_oop(disc_addr);
-      assert(oopDesc::is_null(next_oop) || oopDesc::is_null(disc_oop),
-           err_msg("Found an inactive reference " PTR_FORMAT " with a non-NULL"
-                   "discovered field", p2i(obj)));
+      if(TraceReferenceGC && PrintGCDetails) {
+        gclog_or_tty->print_cr("   Process discovered as normal "
+                               PTR_FORMAT, p2i(disc_addr));
+      }
     )
+    Devirtualizer<nv>::do_oop(closure, disc_addr);
   }
   // treat next as normal oop
   if (contains(next_addr)) {
--- a/hotspot/src/share/vm/oops/klassVtable.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/oops/klassVtable.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1054,7 +1054,7 @@
 
 int klassItable::assign_itable_indices_for_interface(Klass* klass) {
   // an interface does not have an itable, but its methods need to be numbered
-  if (TraceItables) tty->print_cr("%3d: Initializing itable for interface %s", ++initialize_count,
+  if (TraceItables) tty->print_cr("%3d: Initializing itable indices for interface %s", ++initialize_count,
                                   klass->name()->as_C_string());
   Array<Method*>* methods = InstanceKlass::cast(klass)->methods();
   int nof_methods = methods->length();
@@ -1068,7 +1068,7 @@
         ResourceMark rm;
         const char* sig = (m != NULL) ? m->name_and_sig_as_C_string() : "<NULL>";
         if (m->has_vtable_index()) {
-          tty->print("itable index %d for method: %s, flags: ", m->vtable_index(), sig);
+          tty->print("vtable index %d for method: %s, flags: ", m->vtable_index(), sig);
         } else {
           tty->print("itable index %d for method: %s, flags: ", ime_num, sig);
         }
@@ -1100,22 +1100,25 @@
   assert(interf->is_interface(), "must be");
   Array<Method*>* methods = InstanceKlass::cast(interf)->methods();
   int nof_methods = methods->length();
+  int length = 0;
   while (nof_methods > 0) {
     Method* m = methods->at(nof_methods-1);
     if (m->has_itable_index()) {
-      int length = m->itable_index() + 1;
-#ifdef ASSERT
-      while (nof_methods = 0) {
-        m = methods->at(--nof_methods);
-        assert(!m->has_itable_index() || m->itable_index() < length, "");
-      }
-#endif //ASSERT
-      return length;  // return the rightmost itable index, plus one
+      length = m->itable_index() + 1;
+      break;
     }
     nof_methods -= 1;
   }
-  // no methods have itable indices
-  return 0;
+#ifdef ASSERT
+  int nof_methods_copy = nof_methods;
+  while (nof_methods_copy > 0) {
+    Method* mm = methods->at(--nof_methods_copy);
+    assert(!mm->has_itable_index() || mm->itable_index() < length, "");
+  }
+#endif //ASSERT
+  // return the rightmost itable index, plus one; or 0 if no methods have
+  // itable indices
+  return length;
 }
 
 
--- a/hotspot/src/share/vm/opto/arraycopynode.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/arraycopynode.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,9 @@
   : CallNode(arraycopy_type(), NULL, TypeRawPtr::BOTTOM),
     _alloc_tightly_coupled(alloc_tightly_coupled),
     _kind(None),
-    _arguments_validated(false) {
+    _arguments_validated(false),
+    _src_type(TypeOopPtr::BOTTOM),
+    _dest_type(TypeOopPtr::BOTTOM) {
   init_class_id(Class_ArrayCopy);
   init_flags(Flag_is_macro);
   C->add_macro_node(this);
@@ -595,3 +597,17 @@
 
   return mem;
 }
+
+bool ArrayCopyNode::may_modify(const TypeOopPtr *t_oop, PhaseTransform *phase) {
+  const TypeOopPtr* dest_t = phase->type(in(ArrayCopyNode::Dest))->is_oopptr();
+  assert(!dest_t->is_known_instance() || _dest_type->is_known_instance(), "result of EA not recorded");
+  const TypeOopPtr* src_t = phase->type(in(ArrayCopyNode::Src))->is_oopptr();
+  assert(!src_t->is_known_instance() || _src_type->is_known_instance(), "result of EA not recorded");
+
+  if (_dest_type != TypeOopPtr::BOTTOM || t_oop->is_known_instance()) {
+    assert(_dest_type == TypeOopPtr::BOTTOM || _dest_type->is_known_instance(), "result of EA is known instance");
+    return t_oop->instance_id() == _dest_type->instance_id();
+  }
+
+  return CallNode::may_modify_arraycopy_helper(dest_t, t_oop, phase);
+}
--- a/hotspot/src/share/vm/opto/arraycopynode.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/arraycopynode.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -124,6 +124,10 @@
     ParmLimit
   };
 
+  // Results from escape analysis for non escaping inputs
+  const TypeOopPtr* _src_type;
+  const TypeOopPtr* _dest_type;
+
   static ArrayCopyNode* make(GraphKit* kit, bool may_throw,
                              Node* src, Node* src_offset,
                              Node* dest,  Node* dest_offset,
@@ -154,11 +158,12 @@
   virtual bool guaranteed_safepoint()  { return false; }
   virtual Node *Ideal(PhaseGVN *phase, bool can_reshape);
 
+  virtual bool may_modify(const TypeOopPtr *t_oop, PhaseTransform *phase);
+
   bool is_alloc_tightly_coupled() const { return _alloc_tightly_coupled; }
 
 #ifndef PRODUCT
   virtual void dump_spec(outputStream *st) const;
 #endif
 };
-
 #endif // SHARE_VM_OPTO_ARRAYCOPYNODE_HPP
--- a/hotspot/src/share/vm/opto/c2_globals.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/c2_globals.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -96,7 +96,7 @@
   product(intx, MaxLoopPad, (OptoLoopAlignment-1),                          \
           "Align a loop if padding size in bytes is less or equal to this value") \
                                                                             \
-  product(intx, MaxVectorSize, 32,                                          \
+  product(intx, MaxVectorSize, 64,                                          \
           "Max vector size in bytes, "                                      \
           "actual size could be less depending on elements type")           \
                                                                             \
@@ -318,6 +318,9 @@
   notproduct(bool, TraceLoopUnswitching, false,                             \
           "Trace loop unswitching")                                         \
                                                                             \
+  product(bool, AllowVectorizeOnDemand, true,                               \
+          "Globally supress vectorization set in VectorizeMethod")          \
+                                                                            \
   product(bool, UseSuperWord, true,                                         \
           "Transform scalar operations into superword operations")          \
                                                                             \
--- a/hotspot/src/share/vm/opto/callnode.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/callnode.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -797,11 +797,12 @@
       }
       cast = use;
     } else if (!use->is_Initialize() &&
-               !use->is_AddP()) {
+               !use->is_AddP() &&
+               use->Opcode() != Op_MemBarStoreStore) {
       // Expected uses are restricted to a CheckCastPP, an Initialize
-      // node, and AddP nodes. If we encounter any other use (a Phi
-      // node can be seen in rare cases) return this to prevent
-      // incorrect optimizations.
+      // node, a MemBarStoreStore (clone) and AddP nodes. If we
+      // encounter any other use (a Phi node can be seen in rare
+      // cases) return this to prevent incorrect optimizations.
       return this;
     }
   }
@@ -1006,6 +1007,14 @@
 
 
 //=============================================================================
+bool CallLeafNode::is_call_to_arraycopystub() const {
+  if (_name != NULL && strstr(_name, "arraycopy") != 0) {
+    return true;
+  }
+  return false;
+}
+
+
 #ifndef PRODUCT
 void CallLeafNode::dump_spec(outputStream *st) const {
   st->print("# ");
@@ -1875,3 +1884,72 @@
     log->tail(tag);
   }
 }
+
+bool CallNode::may_modify_arraycopy_helper(const TypeOopPtr* dest_t, const TypeOopPtr *t_oop, PhaseTransform *phase) {
+  if (dest_t->is_known_instance() && t_oop->is_known_instance()) {
+    return dest_t->instance_id() == t_oop->instance_id();
+  }
+
+  if (dest_t->isa_instptr() && !dest_t->klass()->equals(phase->C->env()->Object_klass())) {
+    // clone
+    if (t_oop->isa_aryptr()) {
+      return false;
+    }
+    if (!t_oop->isa_instptr()) {
+      return true;
+    }
+    if (dest_t->klass()->is_subtype_of(t_oop->klass()) || t_oop->klass()->is_subtype_of(dest_t->klass())) {
+      return true;
+    }
+    // unrelated
+    return false;
+  }
+
+  if (dest_t->isa_aryptr()) {
+    // arraycopy or array clone
+    if (t_oop->isa_instptr()) {
+      return false;
+    }
+    if (!t_oop->isa_aryptr()) {
+      return true;
+    }
+
+    const Type* elem = dest_t->is_aryptr()->elem();
+    if (elem == Type::BOTTOM) {
+      // An array but we don't know what elements are
+      return true;
+    }
+
+    dest_t = dest_t->add_offset(Type::OffsetBot)->is_oopptr();
+    uint dest_alias = phase->C->get_alias_index(dest_t);
+    uint t_oop_alias = phase->C->get_alias_index(t_oop);
+
+    return dest_alias == t_oop_alias;
+  }
+
+  return true;
+}
+
+bool CallLeafNode::may_modify(const TypeOopPtr *t_oop, PhaseTransform *phase) {
+  if (is_call_to_arraycopystub()) {
+    const TypeTuple* args = _tf->domain();
+    Node* dest = NULL;
+    // Stubs that can be called once an ArrayCopyNode is expanded have
+    // different signatures. Look for the second pointer argument,
+    // that is the destination of the copy.
+    for (uint i = TypeFunc::Parms, j = 0; i < args->cnt(); i++) {
+      if (args->field_at(i)->isa_ptr()) {
+        j++;
+        if (j == 2) {
+          dest = in(i);
+          break;
+        }
+      }
+    }
+    if (may_modify_arraycopy_helper(phase->type(dest)->is_oopptr(), t_oop, phase)) {
+      return true;
+    }
+    return false;
+  }
+  return CallNode::may_modify(t_oop, phase);
+}
--- a/hotspot/src/share/vm/opto/callnode.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/callnode.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -556,6 +556,10 @@
 // contain the functionality of a full scope chain of debug nodes.
 class CallNode : public SafePointNode {
   friend class VMStructs;
+
+protected:
+  bool may_modify_arraycopy_helper(const TypeOopPtr* dest_t, const TypeOopPtr *t_oop, PhaseTransform *phase);
+
 public:
   const TypeFunc *_tf;        // Function type
   address      _entry_point;  // Address of method being called
@@ -781,6 +785,8 @@
 #ifndef PRODUCT
   virtual void  dump_spec(outputStream *st) const;
 #endif
+  bool is_call_to_arraycopystub() const;
+  virtual bool may_modify(const TypeOopPtr *t_oop, PhaseTransform *phase);
 };
 
 //------------------------------CallLeafNoFPNode-------------------------------
@@ -1082,5 +1088,4 @@
   JVMState* dbg_jvms() const { return NULL; }
 #endif
 };
-
 #endif // SHARE_VM_OPTO_CALLNODE_HPP
--- a/hotspot/src/share/vm/opto/chaitin.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/chaitin.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -907,6 +907,13 @@
           lrg.set_num_regs(RegMask::SlotsPerVecY);
           lrg.set_reg_pressure(1);
           break;
+        case Op_VecZ:
+          assert(Matcher::vector_size_supported(T_FLOAT,RegMask::SlotsPerVecZ), "sanity");
+          assert(RegMask::num_registers(Op_VecZ) == RegMask::SlotsPerVecZ, "sanity");
+          assert(lrgmask.is_aligned_sets(RegMask::SlotsPerVecZ), "vector should be aligned");
+          lrg.set_num_regs(RegMask::SlotsPerVecZ);
+          lrg.set_reg_pressure(1);
+          break;
         default:
           ShouldNotReachHere();
         }
@@ -1514,7 +1521,7 @@
       int n_regs = lrg->num_regs();
       assert(!lrg->_is_vector || !lrg->_fat_proj, "sanity");
       if (n_regs == 1 || !lrg->_fat_proj) {
-        assert(!lrg->_is_vector || n_regs <= RegMask::SlotsPerVecY, "sanity");
+        assert(!lrg->_is_vector || n_regs <= RegMask::SlotsPerVecZ, "sanity");
         lrg->Clear();           // Clear the mask
         lrg->Insert(reg);       // Set regmask to match selected reg
         // For vectors and pairs, also insert the low bit of the pair
--- a/hotspot/src/share/vm/opto/chaitin.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/chaitin.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -141,7 +141,7 @@
 
   // Number of registers this live range uses when it colors
 private:
-  uint8_t _num_regs;            // 2 for Longs and Doubles, 1 for all else
+  uint16_t _num_regs;           // 2 for Longs and Doubles, 1 for all else
                                 // except _num_regs is kill count for fat_proj
 public:
   int num_regs() const { return _num_regs; }
@@ -150,7 +150,7 @@
 private:
   // Number of physical registers this live range uses when it colors
   // Architecture and register-set dependent
-  uint8_t _reg_pressure;
+  uint16_t _reg_pressure;
 public:
   void set_reg_pressure(int i)  { _reg_pressure = i; }
   int      reg_pressure() const { return _reg_pressure; }
--- a/hotspot/src/share/vm/opto/classes.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/classes.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -282,6 +282,8 @@
 macro(MulVS)
 macro(MulVI)
 macro(MulReductionVI)
+macro(MulVL)
+macro(MulReductionVL)
 macro(MulVF)
 macro(MulReductionVF)
 macro(MulVD)
--- a/hotspot/src/share/vm/opto/compile.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/compile.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -453,6 +453,8 @@
   assert(compile == Compile::current(), "sanity");
 
   compile->set_type_dict(NULL);
+  compile->set_clone_map(new Dict(cmpkey, hashkey, _compile->comp_arena()));
+  compile->clone_map().set_clone_idx(0);
   compile->set_type_hwm(NULL);
   compile->set_type_last_size(0);
   compile->set_last_tf(NULL, NULL);
@@ -462,6 +464,7 @@
   Type::Initialize(compile);
   _compile->set_scratch_buffer_blob(NULL);
   _compile->begin_method();
+  _compile->clone_map().set_debug(_compile->has_method() && _compile->method_has_option(_compile->clone_map().debug_option_name));
 }
 CompileWrapper::~CompileWrapper() {
   _compile->end_method();
@@ -1091,6 +1094,24 @@
   set_do_scheduling(OptoScheduling);
   set_do_count_invocations(false);
   set_do_method_data_update(false);
+
+  set_do_vector_loop(false);
+
+  bool do_vector = false;
+  if (AllowVectorizeOnDemand) {
+    if (has_method() && (method()->has_option("Vectorize") || method()->has_option("VectorizeDebug"))) {
+      set_do_vector_loop(true);
+    } else if (has_method() && method()->name() != 0 &&
+               method()->intrinsic_id() == vmIntrinsics::_forEachRemaining) {
+      set_do_vector_loop(true);
+    }
+#ifndef PRODUCT
+    if (do_vector_loop() && Verbose) {
+      tty->print("Compile::Init: do vectorized loops (SIMD like) for method %s\n",  method()->name()->as_quoted_ascii());
+    }
+#endif
+  }
+
   set_age_code(has_method() && method()->profile_aging());
   set_rtm_state(NoRTM); // No RTM lock eliding by default
   method_has_option_value("MaxNodeLimit", _max_node_limit);
@@ -3089,6 +3110,7 @@
   case Op_AddReductionVF:
   case Op_AddReductionVD:
   case Op_MulReductionVI:
+  case Op_MulReductionVL:
   case Op_MulReductionVF:
   case Op_MulReductionVD:
     break;
@@ -4334,3 +4356,63 @@
   assert(count > 0, "only positive");
   return (os::random() & RANDOMIZED_DOMAIN_MASK) < (RANDOMIZED_DOMAIN / count);
 }
+
+const char*   CloneMap::debug_option_name = "CloneMapDebug";
+CloneMap&     Compile::clone_map()                 { return _clone_map; }
+void          Compile::set_clone_map(Dict* d)      { _clone_map._dict = d; }
+
+void NodeCloneInfo::dump() const {
+  tty->print(" {%d:%d} ", idx(), gen());
+}
+
+void CloneMap::clone(Node* old, Node* nnn, int gen) {
+  uint64_t val = value(old->_idx);
+  NodeCloneInfo cio(val);
+  assert(val != 0, "old node should be in the map");
+  NodeCloneInfo cin(cio.idx(), gen + cio.gen());
+  insert(nnn->_idx, cin.get());
+#ifndef PRODUCT
+  if (is_debug()) {
+    tty->print_cr("CloneMap::clone inserted node %d info {%d:%d} into CloneMap", nnn->_idx, cin.idx(), cin.gen());
+  }
+#endif
+}
+
+void CloneMap::verify_insert_and_clone(Node* old, Node* nnn, int gen) {
+  NodeCloneInfo cio(value(old->_idx));
+  if (cio.get() == 0) {
+    cio.set(old->_idx, 0);
+    insert(old->_idx, cio.get());
+#ifndef PRODUCT
+    if (is_debug()) {
+      tty->print_cr("CloneMap::verify_insert_and_clone inserted node %d info {%d:%d} into CloneMap", old->_idx, cio.idx(), cio.gen());
+    }
+#endif
+  }
+  clone(old, nnn, gen);
+}
+
+int CloneMap::max_gen() const {
+  int g = 0;
+  DictI di(_dict);
+  for(; di.test(); ++di) {
+    int t = gen(di._key);
+    if (g < t) {
+      g = t;
+#ifndef PRODUCT
+      if (is_debug()) {
+        tty->print_cr("CloneMap::max_gen() update max=%d from %d", g, _2_node_idx_t(di._key));
+      }
+#endif
+    }
+  }
+  return g;
+}
+
+void CloneMap::dump(node_idx_t key) const {
+  uint64_t val = value(key);
+  if (val != 0) {
+    NodeCloneInfo ni(val);
+    ni.dump();
+  }
+}
--- a/hotspot/src/share/vm/opto/compile.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/compile.hpp	Wed Jul 05 20:35:10 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
@@ -47,6 +47,7 @@
 class Bundle;
 class C2Compiler;
 class CallGenerator;
+class CloneMap;
 class ConnectionGraph;
 class InlineTree;
 class Int_Array;
@@ -59,6 +60,7 @@
 class Node;
 class Node_Array;
 class Node_Notes;
+class NodeCloneInfo;
 class OptoReg;
 class PhaseCFG;
 class PhaseGVN;
@@ -84,6 +86,62 @@
 class Node_Stack;
 struct Final_Reshape_Counts;
 
+typedef unsigned int node_idx_t;
+class NodeCloneInfo {
+ private:
+  uint64_t  _idx_clone_orig;
+ public:
+
+  void set_idx(node_idx_t idx) {
+    _idx_clone_orig = _idx_clone_orig & 0xFFFFFFFF00000000 | idx;
+  }
+  node_idx_t idx() const { return (node_idx_t)(_idx_clone_orig & 0xFFFFFFFF); }
+
+  void set_gen(int generation) {
+    uint64_t  g = (uint64_t)generation << 32;
+    _idx_clone_orig = _idx_clone_orig & 0xFFFFFFFF | g;
+  }
+  int gen() const { return (int)(_idx_clone_orig >> 32); }
+
+  void set(uint64_t x) {  _idx_clone_orig = x; }
+  void set(node_idx_t x, int g) {  set_idx(x); set_gen(g); }
+  uint64_t get() const { return _idx_clone_orig; }
+
+  NodeCloneInfo(uint64_t idx_clone_orig) : _idx_clone_orig(idx_clone_orig) {}
+  NodeCloneInfo(node_idx_t x, int g) {set(x, g);}
+
+  void dump() const;
+};
+
+class CloneMap {
+  friend class Compile;
+ private:
+  bool      _debug;
+  Dict*     _dict;
+  int       _clone_idx;   // current cloning iteration/generation in loop unroll
+ public:
+  void*     _2p(node_idx_t key)   const          { return (void*)(intptr_t)key; } // 2 conversion functions to make gcc happy
+  node_idx_t _2_node_idx_t(const void* k) const  { return (node_idx_t)(intptr_t)k; }
+  Dict*     dict()                const          { return _dict; }
+  void insert(node_idx_t key, uint64_t val)      { assert(_dict->operator[](_2p(key)) == NULL, "key existed"); _dict->Insert(_2p(key), (void*)val); }
+  void insert(node_idx_t key, NodeCloneInfo& ci) { insert(key, ci.get()); }
+  void remove(node_idx_t key)                    { _dict->Delete(_2p(key)); }
+  uint64_t value(node_idx_t key)  const          { return (uint64_t)_dict->operator[](_2p(key)); }
+  node_idx_t idx(node_idx_t key)  const          { return NodeCloneInfo(value(key)).idx(); }
+  int gen(node_idx_t key)         const          { return NodeCloneInfo(value(key)).gen(); }
+  int gen(const void* k)          const          { return gen(_2_node_idx_t(k)); }
+  int max_gen()                   const;
+  void clone(Node* old, Node* nnn, int gen);
+  void verify_insert_and_clone(Node* old, Node* nnn, int gen);
+  void dump(node_idx_t key)       const;
+
+  int  clone_idx() const                         { return _clone_idx; }
+  void set_clone_idx(int x)                      { _clone_idx = x; }
+  bool is_debug()                 const          { return _debug; }
+  void set_debug(bool debug)                     { _debug = debug; }
+  static const char* debug_option_name;
+};
+
 //------------------------------Compile----------------------------------------
 // This class defines a top-level Compiler invocation.
 
@@ -312,6 +370,7 @@
   bool                  _do_freq_based_layout;  // True if we intend to do frequency based block layout
   bool                  _do_count_invocations;  // True if we generate code to count invocations
   bool                  _do_method_data_update; // True if we generate code to update MethodData*s
+  bool                  _do_vector_loop;        // True if allowed to execute loop in parallel iterations
   bool                  _age_code;              // True if we need to profile code age (decrement the aging counter)
   int                   _AliasLevel;            // Locally-adjusted version of AliasLevel flag.
   bool                  _print_assembly;        // True if we should dump assembly code for this compilation
@@ -380,6 +439,7 @@
   Arena                 _Compile_types;         // Arena for all types
   Arena*                _type_arena;            // Alias for _Compile_types except in Initialize_shared()
   Dict*                 _type_dict;             // Intern table
+  CloneMap              _clone_map;             // used for recording history of cloned nodes
   void*                 _type_hwm;              // Last allocation (see Type::operator new/delete)
   size_t                _type_last_size;        // Last allocation size (see Type::operator new/delete)
   ciMethod*             _last_tf_m;             // Cache for
@@ -586,6 +646,8 @@
   void          set_do_count_invocations(bool z){ _do_count_invocations = z; }
   bool              do_method_data_update() const { return _do_method_data_update; }
   void          set_do_method_data_update(bool z) { _do_method_data_update = z; }
+  bool              do_vector_loop() const      { return _do_vector_loop; }
+  void          set_do_vector_loop(bool z)      { _do_vector_loop = z; }
   bool              age_code() const             { return _age_code; }
   void          set_age_code(bool z)             { _age_code = z; }
   int               AliasLevel() const           { return _AliasLevel; }
@@ -1228,6 +1290,11 @@
 
   // Auxiliary method for randomized fuzzing/stressing
   static bool randomized_select(int count);
+
+  // supporting clone_map
+  CloneMap&     clone_map();
+  void          set_clone_map(Dict* d);
+
 };
 
 #endif // SHARE_VM_OPTO_COMPILE_HPP
--- a/hotspot/src/share/vm/opto/escape.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/escape.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -28,6 +28,7 @@
 #include "libadt/vectset.hpp"
 #include "memory/allocation.hpp"
 #include "opto/c2compiler.hpp"
+#include "opto/arraycopynode.hpp"
 #include "opto/callnode.hpp"
 #include "opto/cfgnode.hpp"
 #include "opto/compile.hpp"
@@ -113,6 +114,7 @@
   GrowableArray<Node*> alloc_worklist;
   GrowableArray<Node*> ptr_cmp_worklist;
   GrowableArray<Node*> storestore_worklist;
+  GrowableArray<ArrayCopyNode*> arraycopy_worklist;
   GrowableArray<PointsToNode*>   ptnodes_worklist;
   GrowableArray<JavaObjectNode*> java_objects_worklist;
   GrowableArray<JavaObjectNode*> non_escaped_worklist;
@@ -173,6 +175,10 @@
       // Collect address nodes for graph verification.
       addp_worklist.append(n);
 #endif
+    } else if (n->is_ArrayCopy()) {
+      // Keep a list of ArrayCopy nodes so if one of its input is non
+      // escaping, we can record a unique type
+      arraycopy_worklist.append(n->as_ArrayCopy());
     }
     for (DUIterator_Fast imax, i = n->fast_outs(imax); i < imax; i++) {
       Node* m = n->fast_out(i);   // Get user
@@ -289,7 +295,7 @@
       C->AliasLevel() >= 3 && EliminateAllocations) {
     // Now use the escape information to create unique types for
     // scalar replaceable objects.
-    split_unique_types(alloc_worklist);
+    split_unique_types(alloc_worklist, arraycopy_worklist);
     if (C->failing())  return false;
     C->print_method(PHASE_AFTER_EA, 2);
 
@@ -333,7 +339,7 @@
 // Populate Connection Graph with PointsTo nodes and create simple
 // connection graph edges.
 void ConnectionGraph::add_node_to_connection_graph(Node *n, Unique_Node_List *delayed_worklist) {
-  assert(!_verify, "this method sould not be called for verification");
+  assert(!_verify, "this method should not be called for verification");
   PhaseGVN* igvn = _igvn;
   uint n_idx = n->_idx;
   PointsToNode* n_ptn = ptnode_adr(n_idx);
@@ -901,8 +907,7 @@
       // are still a few direct calls to the copy subroutines (See
       // PhaseStringOpts::copy_string())
       is_arraycopy = (call->Opcode() == Op_ArrayCopy) ||
-        (call->as_CallLeaf()->_name != NULL &&
-         strstr(call->as_CallLeaf()->_name, "arraycopy") != 0);
+        call->as_CallLeaf()->is_call_to_arraycopystub();
       // fall through
     case Op_CallLeaf: {
       // Stub calls, objects do not escape but they are not scale replaceable.
@@ -980,7 +985,17 @@
               !arg_is_arraycopy_dest) {
             continue;
           }
-          set_escape_state(arg_ptn, PointsToNode::ArgEscape);
+          PointsToNode::EscapeState es = PointsToNode::ArgEscape;
+          if (call->is_ArrayCopy()) {
+            ArrayCopyNode* ac = call->as_ArrayCopy();
+            if (ac->is_clonebasic() ||
+                ac->is_arraycopy_validated() ||
+                ac->is_copyof_validated() ||
+                ac->is_copyofrange_validated()) {
+              es = PointsToNode::NoEscape;
+            }
+          }
+          set_escape_state(arg_ptn, es);
           if (arg_is_arraycopy_dest) {
             Node* src = call->in(TypeFunc::Parms);
             if (src->is_AddP()) {
@@ -994,7 +1009,7 @@
               // as base since objects escape states are not related.
               // Only escape state of destination object's fields affects
               // escape state of fields in source object.
-              add_arraycopy(call, PointsToNode::ArgEscape, src_ptn, arg_ptn);
+              add_arraycopy(call, es, src_ptn, arg_ptn);
             }
           }
         }
@@ -1272,12 +1287,12 @@
         if ((e->escape_state() < field_es) &&
             e->is_Field() && ptn->is_JavaObject() &&
             e->as_Field()->is_oop()) {
-          // Change escape state of referenced fileds.
+          // Change escape state of referenced fields.
           set_escape_state(e, field_es);
-          es_changed = true;;
+          es_changed = true;
         } else if (e->escape_state() < es) {
           set_escape_state(e, es);
-          es_changed = true;;
+          es_changed = true;
         }
         if (es_changed) {
           escape_worklist.push(e);
@@ -1389,7 +1404,7 @@
           for (UseIterator k(arycp); k.has_next(); k.next()) {
             PointsToNode* abase = k.get();
             if (abase->arraycopy_dst() && abase != base) {
-              // Look for the same arracopy reference.
+              // Look for the same arraycopy reference.
               add_fields_to_worklist(field, abase);
             }
           }
@@ -1469,12 +1484,13 @@
   int new_edges = 0;
   Node* alloc = pta->ideal_node();
   if (init_val == phantom_obj) {
-    // Do nothing for Allocate nodes since its fields values are "known".
-    if (alloc->is_Allocate())
+    // Do nothing for Allocate nodes since its fields values are
+    // "known" unless they are initialized by arraycopy/clone.
+    if (alloc->is_Allocate() && !pta->arraycopy_dst())
       return 0;
-    assert(alloc->as_CallStaticJava(), "sanity");
+    assert(pta->arraycopy_dst() || alloc->as_CallStaticJava(), "sanity");
 #ifdef ASSERT
-    if (alloc->as_CallStaticJava()->method() == NULL) {
+    if (!pta->arraycopy_dst() && alloc->as_CallStaticJava()->method() == NULL) {
       const char* name = alloc->as_CallStaticJava()->_name;
       assert(strncmp(name, "_multianewarray", 15) == 0, "sanity");
     }
@@ -1623,11 +1639,12 @@
   //
   for (UseIterator i(jobj); i.has_next(); i.next()) {
     PointsToNode* use = i.get();
-    assert(!use->is_Arraycopy(), "sanity");
+    if (use->is_Arraycopy()) {
+      continue;
+    }
     if (use->is_Field()) {
       FieldNode* field = use->as_Field();
-      assert(field->is_oop() && field->scalar_replaceable() &&
-             field->fields_escape_state() == PointsToNode::NoEscape, "sanity");
+      assert(field->is_oop() && field->scalar_replaceable(), "sanity");
       if (field->offset() == Type::OffsetBot) {
         jobj->set_scalar_replaceable(false);
         return;
@@ -1660,6 +1677,10 @@
   }
 
   for (EdgeIterator j(jobj); j.has_next(); j.next()) {
+    if (j.get()->is_Arraycopy()) {
+      continue;
+    }
+
     // Non-escaping object node should point only to field nodes.
     FieldNode* field = j.get()->as_Field();
     int offset = field->as_Field()->offset();
@@ -2636,6 +2657,7 @@
       if (proj_in->is_Allocate() && proj_in->_idx == (uint)toop->instance_id()) {
         break;  // hit one of our sentinels
       } else if (proj_in->is_Call()) {
+        // ArrayCopy node processed here as well
         CallNode *call = proj_in->as_Call();
         if (!call->may_modify(toop, igvn)) {
           result = call->in(TypeFunc::Memory);
@@ -2648,6 +2670,15 @@
           result = proj_in->in(TypeFunc::Memory);
         }
       } else if (proj_in->is_MemBar()) {
+        if (proj_in->in(TypeFunc::Memory)->is_MergeMem() &&
+            proj_in->in(TypeFunc::Memory)->as_MergeMem()->in(Compile::AliasIdxRaw)->is_Proj() &&
+            proj_in->in(TypeFunc::Memory)->as_MergeMem()->in(Compile::AliasIdxRaw)->in(0)->is_ArrayCopy()) {
+          // clone
+          ArrayCopyNode* ac = proj_in->in(TypeFunc::Memory)->as_MergeMem()->in(Compile::AliasIdxRaw)->in(0)->as_ArrayCopy();
+          if (ac->may_modify(toop, igvn)) {
+            break;
+          }
+        }
         result = proj_in->in(TypeFunc::Memory);
       }
     } else if (result->is_MergeMem()) {
@@ -2724,7 +2755,7 @@
 //
 //  Phase 1:  Process possible allocations from alloc_worklist.  Create instance
 //            types for the CheckCastPP for allocations where possible.
-//            Propagate the the new types through users as follows:
+//            Propagate the new types through users as follows:
 //               casts and Phi:  push users on alloc_worklist
 //               AddP:  cast Base and Address inputs to the instance type
 //                      push any AddP users on alloc_worklist and push any memnode
@@ -2803,7 +2834,7 @@
 //    90  LoadP    _ 120  30   ... alias_index=6
 //   100  LoadP    _  80  20   ... alias_index=4
 //
-void ConnectionGraph::split_unique_types(GrowableArray<Node *>  &alloc_worklist) {
+void ConnectionGraph::split_unique_types(GrowableArray<Node *>  &alloc_worklist, GrowableArray<ArrayCopyNode*> &arraycopy_worklist) {
   GrowableArray<Node *>  memnode_worklist;
   GrowableArray<PhiNode *>  orig_phis;
   PhaseIterGVN  *igvn = _igvn;
@@ -2912,9 +2943,12 @@
       if (alloc->is_Allocate() && (t->isa_instptr() || t->isa_aryptr())) {
 
         // First, put on the worklist all Field edges from Connection Graph
-        // which is more accurate then putting immediate users from Ideal Graph.
+        // which is more accurate than putting immediate users from Ideal Graph.
         for (EdgeIterator e(ptn); e.has_next(); e.next()) {
           PointsToNode* tgt = e.get();
+          if (tgt->is_Arraycopy()) {
+            continue;
+          }
           Node* use = tgt->ideal_node();
           assert(tgt->is_Field() && use->is_AddP(),
                  "only AddP nodes are Field edges in CG");
@@ -3068,6 +3102,38 @@
     }
 
   }
+
+  // Go over all ArrayCopy nodes and if one of the inputs has a unique
+  // type, record it in the ArrayCopy node so we know what memory this
+  // node uses/modified.
+  for (int next = 0; next < arraycopy_worklist.length(); next++) {
+    ArrayCopyNode* ac = arraycopy_worklist.at(next);
+    Node* dest = ac->in(ArrayCopyNode::Dest);
+    if (dest->is_AddP()) {
+      dest = get_addp_base(dest);
+    }
+    JavaObjectNode* jobj = unique_java_object(dest);
+    if (jobj != NULL) {
+      Node *base = get_map(jobj->idx());
+      if (base != NULL) {
+        const TypeOopPtr *base_t = _igvn->type(base)->isa_oopptr();
+        ac->_dest_type = base_t;
+      }
+    }
+    Node* src = ac->in(ArrayCopyNode::Src);
+    if (src->is_AddP()) {
+      src = get_addp_base(src);
+    }
+    jobj = unique_java_object(src);
+    if (jobj != NULL) {
+      Node* base = get_map(jobj->idx());
+      if (base != NULL) {
+        const TypeOopPtr *base_t = _igvn->type(base)->isa_oopptr();
+        ac->_src_type = base_t;
+      }
+    }
+  }
+
   // New alias types were created in split_AddP().
   uint new_index_end = (uint) _compile->num_alias_types();
   assert(unique_old == _compile->unique(), "there should be no new ideal nodes after Phase 1");
--- a/hotspot/src/share/vm/opto/escape.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/escape.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -536,7 +536,7 @@
 
   // Propagate unique types created for unescaped allocated objects
   // through the graph
-  void split_unique_types(GrowableArray<Node *>  &alloc_worklist);
+  void split_unique_types(GrowableArray<Node *>  &alloc_worklist, GrowableArray<ArrayCopyNode*> &arraycopy_worklist);
 
   // Helper methods for unique types split.
   bool split_AddP(Node *addp, Node *base);
--- a/hotspot/src/share/vm/opto/gcm.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/gcm.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -483,7 +483,7 @@
 
   // Compute the alias index.  Loads and stores with different alias indices
   // do not need anti-dependence edges.
-  uint load_alias_idx = C->get_alias_index(load->adr_type());
+  int load_alias_idx = C->get_alias_index(load->adr_type());
 #ifdef ASSERT
   if (load_alias_idx == Compile::AliasIdxBot && C->AliasLevel() > 0 &&
       (PrintOpto || VerifyAliases ||
--- a/hotspot/src/share/vm/opto/idealGraphPrinter.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/idealGraphPrinter.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2007, 2014, 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
@@ -58,7 +58,7 @@
 const char *IdealGraphPrinter::GRAPH_NAME_PROPERTY = "name";
 const char *IdealGraphPrinter::INDEX_PROPERTY = "index";
 const char *IdealGraphPrinter::METHOD_ELEMENT = "method";
-const char *IdealGraphPrinter::INLINE_ELEMENT = "inline";
+const char *IdealGraphPrinter::INLINE_ELEMENT = "inlined";
 const char *IdealGraphPrinter::BYTECODES_ELEMENT = "bytecodes";
 const char *IdealGraphPrinter::METHOD_BCI_PROPERTY = "bci";
 const char *IdealGraphPrinter::METHOD_SHORT_NAME_PROPERTY = "shortName";
@@ -236,7 +236,6 @@
 }
 
 void IdealGraphPrinter::print_prop(const char *name, int val) {
-
   stringStream stream;
   stream.print("%d", val);
   print_prop(name, stream.as_string());
@@ -266,22 +265,22 @@
   end_head();
 
   head(BYTECODES_ELEMENT);
-  output()->print_cr("<![CDATA[");
-  method->print_codes_on(output());
-  output()->print_cr("]]>");
+  _xml->print_cr("<![CDATA[");
+  method->print_codes_on(_xml);
+  _xml->print_cr("]]>");
   tail(BYTECODES_ELEMENT);
 
-  head(INLINE_ELEMENT);
-  if (tree != NULL) {
+  if (tree != NULL && tree->subtrees().length() > 0) {
+    head(INLINE_ELEMENT);
     GrowableArray<InlineTree *> subtrees = tree->subtrees();
     for (int i = 0; i < subtrees.length(); i++) {
       print_inline_tree(subtrees.at(i));
     }
+    tail(INLINE_ELEMENT);
   }
-  tail(INLINE_ELEMENT);
 
   tail(METHOD_ELEMENT);
-  output()->flush();
+  _xml->flush();
 }
 
 void IdealGraphPrinter::print_inline_tree(InlineTree *tree) {
@@ -334,13 +333,7 @@
 
   tail(PROPERTIES_ELEMENT);
 
-  if (_stream) {
-    char answer = 0;
-    _xml->flush();
-    int result = _stream->read(&answer, 1);
-    _should_send_method = (answer == 'y');
-  }
-
+  _should_send_method = true;
   this->_current_method = method;
 
   _xml->flush();
@@ -358,7 +351,7 @@
 
 // Print indent
 void IdealGraphPrinter::print_indent() {
-  tty->print_cr("printing ident %d", _depth);
+  tty->print_cr("printing indent %d", _depth);
   for (int i = 0; i < _depth; i++) {
     _xml->print("%s", INDENT);
   }
@@ -372,22 +365,17 @@
   _traverse_outs = b;
 }
 
-intptr_t IdealGraphPrinter::get_node_id(Node *n) {
-  return (intptr_t)(n);
-}
-
 void IdealGraphPrinter::visit_node(Node *n, bool edges, VectorSet* temp_set) {
 
   if (edges) {
 
     // Output edge
-    intptr_t dest_id = get_node_id(n);
+    node_idx_t dest_id = n->_idx;
     for ( uint i = 0; i < n->len(); i++ ) {
       if ( n->in(i) ) {
         Node *source = n->in(i);
         begin_elem(EDGE_ELEMENT);
-        intptr_t source_id = get_node_id(source);
-        print_attr(FROM_PROPERTY, source_id);
+        print_attr(FROM_PROPERTY, source->_idx);
         print_attr(TO_PROPERTY, dest_id);
         print_attr(INDEX_PROPERTY, i);
         end_elem();
@@ -398,7 +386,7 @@
 
     // Output node
     begin_head(NODE_ELEMENT);
-    print_attr(NODE_ID_PROPERTY, get_node_id(n));
+    print_attr(NODE_ID_PROPERTY, n->_idx);
     end_head();
 
     head(PROPERTIES_ELEMENT);
@@ -720,7 +708,7 @@
       head(NODES_ELEMENT);
       for (uint s = 0; s < block->number_of_nodes(); s++) {
         begin_elem(NODE_ELEMENT);
-        print_attr(NODE_ID_PROPERTY, get_node_id(block->get_node(s)));
+        print_attr(NODE_ID_PROPERTY, block->get_node(s)->_idx);
         end_elem();
       }
       tail(NODES_ELEMENT);
@@ -730,7 +718,7 @@
     tail(CONTROL_FLOW_ELEMENT);
   }
   tail(GRAPH_ELEMENT);
-  output()->flush();
+  _xml->flush();
 }
 
 // Should method be printed?
@@ -742,8 +730,4 @@
 
 extern const char *NodeClassNames[];
 
-outputStream *IdealGraphPrinter::output() {
-  return _xml;
-}
-
 #endif
--- a/hotspot/src/share/vm/opto/idealGraphPrinter.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/idealGraphPrinter.hpp	Wed Jul 05 20:35:10 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
@@ -127,7 +127,6 @@
 
   bool traverse_outs();
   void set_traverse_outs(bool b);
-  outputStream *output();
   void print_inlining(Compile* compile);
   void begin_method(Compile* compile);
   void end_method();
--- a/hotspot/src/share/vm/opto/ifnode.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/ifnode.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -834,10 +834,10 @@
     swap(lo_type, hi_type);
     swap(lo_test, hi_test);
 
-    assert((this_bool->_test.is_less() && proj->_con) ||
-           (this_bool->_test.is_greater() && !proj->_con), "incorrect test");
+    assert((dom_bool->_test.is_less() && proj->_con) ||
+           (dom_bool->_test.is_greater() && !proj->_con), "incorrect test");
     // this test was canonicalized
-    assert(dom_bool->_test.is_less() && !fail->_con, "incorrect test");
+    assert(this_bool->_test.is_less() && !fail->_con, "incorrect test");
 
     cond = (hi_test == BoolTest::le || hi_test == BoolTest::gt) ? BoolTest::gt : BoolTest::ge;
 
@@ -973,21 +973,25 @@
           assert(init_n->Opcode() == Op_ConvI2L, "unexpected first node");
           Node* new_n = igvn->C->conv_I2X_index(igvn, l, array_size);
 
-          for (uint j = 2; j < stack.size(); j++) {
-            Node* n = stack.node_at(j);
-            Node* clone = n->clone();
-            int rep = clone->replace_edge(init_n, new_n);
+          // The type of the ConvI2L may be widen and so the new
+          // ConvI2L may not be better than an existing ConvI2L
+          if (new_n != init_n) {
+            for (uint j = 2; j < stack.size(); j++) {
+              Node* n = stack.node_at(j);
+              Node* clone = n->clone();
+              int rep = clone->replace_edge(init_n, new_n);
+              assert(rep > 0, "can't find expected node?");
+              clone = igvn->transform(clone);
+              init_n = n;
+              new_n = clone;
+            }
+            igvn->hash_delete(use);
+            int rep = use->replace_edge(init_n, new_n);
             assert(rep > 0, "can't find expected node?");
-            clone = igvn->transform(clone);
-            init_n = n;
-            new_n = clone;
-          }
-          igvn->hash_delete(use);
-          int rep = use->replace_edge(init_n, new_n);
-          assert(rep > 0, "can't find expected node?");
-          igvn->transform(use);
-          if (init_n->outcnt() == 0) {
-            igvn->_worklist.push(init_n);
+            igvn->transform(use);
+            if (init_n->outcnt() == 0) {
+              igvn->_worklist.push(init_n);
+            }
           }
         }
       } else if (use->in(0) == NULL && (igvn->type(use)->isa_long() ||
--- a/hotspot/src/share/vm/opto/loopTransform.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/loopTransform.cpp	Wed Jul 05 20:35:10 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
@@ -1210,6 +1210,16 @@
     }
     loop->dump_head();
   }
+
+  if (C->do_vector_loop() && (PrintOpto && VerifyLoopOptimizations || TraceLoopOpts)) {
+    Arena* arena = Thread::current()->resource_area();
+    Node_Stack stack(arena, C->unique() >> 2);
+    Node_List rpo_list;
+    VectorSet visited(arena);
+    visited.set(loop_head->_idx);
+    rpo( loop_head, stack, visited, rpo_list );
+    dump(loop, rpo_list.size(), rpo_list );
+  }
 #endif
 
   // Remember loop node count before unrolling to detect
@@ -1497,6 +1507,30 @@
   }
 
   loop->record_for_igvn();
+
+#ifndef PRODUCT
+  if (C->do_vector_loop() && (PrintOpto && VerifyLoopOptimizations || TraceLoopOpts)) {
+    tty->print("\nnew loop after unroll\n");       loop->dump_head();
+    for (uint i = 0; i < loop->_body.size(); i++) {
+      loop->_body.at(i)->dump();
+    }
+    if(C->clone_map().is_debug()) {
+      tty->print("\nCloneMap\n");
+      Dict* dict = C->clone_map().dict();
+      DictI i(dict);
+      tty->print_cr("Dict@%p[%d] = ", dict, dict->Size());
+      for (int ii = 0; i.test(); ++i, ++ii) {
+        NodeCloneInfo cl((uint64_t)dict->operator[]((void*)i._key));
+        tty->print("%d->%d:%d,", (int)(intptr_t)i._key, cl.idx(), cl.gen());
+        if (ii % 10 == 9) {
+          tty->print_cr(" ");
+        }
+      }
+      tty->print_cr(" ");
+    }
+  }
+#endif
+
 }
 
 //------------------------------do_maximally_unroll----------------------------
--- a/hotspot/src/share/vm/opto/loopnode.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/loopnode.cpp	Wed Jul 05 20:35:10 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
@@ -3678,6 +3678,7 @@
 }
 
 void PhaseIdealLoop::dump( IdealLoopTree *loop, uint idx, Node_List &rpo_list ) const {
+  CloneMap& cm = C->clone_map();
   loop->dump_head();
 
   // Now scan for CFG nodes in the same loop
@@ -3709,6 +3710,7 @@
         cached_idom = find_non_split_ctrl(cached_idom);
       }
       tty->print(" ID:%d",computed_idom->_idx);
+      cm.dump(n->_idx);
       n->dump();
       if( cached_idom != computed_idom ) {
         tty->print_cr("*** BROKEN IDOM!  Computed as: %d, cached as: %d",
@@ -3728,6 +3730,7 @@
           for( uint j = 0; j < loop->_nest; j++ )
             tty->print("  ");
           tty->print(" ");
+          cm.dump(m->_idx);
           m->dump();
         }
       }
--- a/hotspot/src/share/vm/opto/loopopts.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/loopopts.cpp	Wed Jul 05 20:35:10 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
@@ -1267,12 +1267,36 @@
 void PhaseIdealLoop::clone_loop( IdealLoopTree *loop, Node_List &old_new, int dd,
                                  Node* side_by_side_idom) {
 
+#ifndef PRODUCT
+  if (C->do_vector_loop() && PrintOpto) {
+    const char* mname = C->method()->name()->as_quoted_ascii();
+    if (mname != NULL) {
+      tty->print("PhaseIdealLoop::clone_loop: for vectorize method %s\n", mname);
+    }
+  }
+#endif
+
+  CloneMap& cm = C->clone_map();
+  Dict* dict = cm.dict();
+  if (C->do_vector_loop()) {
+    cm.set_clone_idx(cm.max_gen()+1);
+#ifndef PRODUCT
+    if (PrintOpto) {
+      tty->print_cr("PhaseIdealLoop::clone_loop: _clone_idx %d", cm.clone_idx());
+      loop->dump_head();
+    }
+#endif
+  }
+
   // Step 1: Clone the loop body.  Make the old->new mapping.
   uint i;
   for( i = 0; i < loop->_body.size(); i++ ) {
     Node *old = loop->_body.at(i);
     Node *nnn = old->clone();
     old_new.map( old->_idx, nnn );
+    if (C->do_vector_loop()) {
+      cm.verify_insert_and_clone(old, nnn, cm.clone_idx());
+    }
     _igvn.register_new_node_with_optimizer(nnn);
   }
 
@@ -1335,6 +1359,9 @@
 
         // Clone the loop exit control projection
         Node *newuse = use->clone();
+        if (C->do_vector_loop()) {
+          cm.verify_insert_and_clone(use, newuse, cm.clone_idx());
+        }
         newuse->set_req(0,nnn);
         _igvn.register_new_node_with_optimizer(newuse);
         set_loop(newuse, use_loop);
--- a/hotspot/src/share/vm/opto/macro.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/macro.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -26,6 +26,7 @@
 #include "compiler/compileLog.hpp"
 #include "libadt/vectset.hpp"
 #include "opto/addnode.hpp"
+#include "opto/arraycopynode.hpp"
 #include "opto/callnode.hpp"
 #include "opto/castnode.hpp"
 #include "opto/cfgnode.hpp"
@@ -613,7 +614,10 @@
         for (DUIterator_Fast kmax, k = use->fast_outs(kmax);
                                    k < kmax && can_eliminate; k++) {
           Node* n = use->fast_out(k);
-          if (!n->is_Store() && n->Opcode() != Op_CastP2X) {
+          if (!n->is_Store() && n->Opcode() != Op_CastP2X &&
+              !(n->is_ArrayCopy() &&
+                n->as_ArrayCopy()->is_clonebasic() &&
+                n->in(ArrayCopyNode::Dest) == use)) {
             DEBUG_ONLY(disq_node = n;)
             if (n->is_Load() || n->is_LoadStore()) {
               NOT_PRODUCT(fail_eliminate = "Field load";)
@@ -623,6 +627,12 @@
             can_eliminate = false;
           }
         }
+      } else if (use->is_ArrayCopy() &&
+                 (use->as_ArrayCopy()->is_arraycopy_validated() ||
+                  use->as_ArrayCopy()->is_copyof_validated() ||
+                  use->as_ArrayCopy()->is_copyofrange_validated()) &&
+                 use->in(ArrayCopyNode::Dest) == res) {
+        // ok to eliminate
       } else if (use->is_SafePoint()) {
         SafePointNode* sfpt = use->as_SafePoint();
         if (sfpt->is_Call() && sfpt->as_Call()->has_non_debug_use(res)) {
@@ -887,11 +897,49 @@
             }
 #endif
             _igvn.replace_node(n, n->in(MemNode::Memory));
+          } else if (n->is_ArrayCopy()) {
+            // Disconnect ArrayCopy node
+            ArrayCopyNode* ac = n->as_ArrayCopy();
+            assert(ac->is_clonebasic(), "unexpected array copy kind");
+            Node* ctl_proj = ac->proj_out(TypeFunc::Control);
+            Node* mem_proj = ac->proj_out(TypeFunc::Memory);
+            if (ctl_proj != NULL) {
+              _igvn.replace_node(ctl_proj, n->in(0));
+            }
+            if (mem_proj != NULL) {
+              _igvn.replace_node(mem_proj, n->in(TypeFunc::Memory));
+            }
           } else {
             eliminate_card_mark(n);
           }
           k -= (oc2 - use->outcnt());
         }
+      } else if (use->is_ArrayCopy()) {
+        // Disconnect ArrayCopy node
+        ArrayCopyNode* ac = use->as_ArrayCopy();
+        assert(ac->is_arraycopy_validated() ||
+               ac->is_copyof_validated() ||
+               ac->is_copyofrange_validated(), "unsupported");
+        CallProjections callprojs;
+        ac->extract_projections(&callprojs, true);
+
+        _igvn.replace_node(callprojs.fallthrough_ioproj, ac->in(TypeFunc::I_O));
+        _igvn.replace_node(callprojs.fallthrough_memproj, ac->in(TypeFunc::Memory));
+        _igvn.replace_node(callprojs.fallthrough_catchproj, ac->in(TypeFunc::Control));
+
+        // Set control to top. IGVN will remove the remaining projections
+        ac->set_req(0, top());
+        ac->replace_edge(res, top());
+
+        // Disconnect src right away: it can help find new
+        // opportunities for allocation elimination
+        Node* src = ac->in(ArrayCopyNode::Src);
+        ac->replace_edge(src, top());
+        if (src->outcnt() == 0) {
+          _igvn.remove_dead_node(src);
+        }
+
+        _igvn._worklist.push(ac);
       } else {
         eliminate_card_mark(use);
       }
--- a/hotspot/src/share/vm/opto/macroArrayCopy.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/macroArrayCopy.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1097,8 +1097,15 @@
       assert(alloc != NULL, "expect alloc");
     }
 
+    const TypePtr* adr_type = _igvn.type(dest)->is_oopptr()->add_offset(Type::OffsetBot);
+    if (ac->_dest_type != TypeOopPtr::BOTTOM) {
+      adr_type = ac->_dest_type->add_offset(Type::OffsetBot)->is_ptr();
+    }
+    if (ac->_src_type != ac->_dest_type) {
+      adr_type = TypeRawPtr::BOTTOM;
+    }
     generate_arraycopy(ac, alloc, &ctrl, merge_mem, &io,
-                       TypeAryPtr::OOPS, T_OBJECT,
+                       adr_type, T_OBJECT,
                        src, src_offset, dest, dest_offset, length,
                        true, !ac->is_copyofrange());
 
@@ -1152,7 +1159,7 @@
   }
   // (2) src and dest arrays must have elements of the same BasicType
   // Figure out the size and type of the elements we will be copying.
-  BasicType src_elem  =  top_src->klass()->as_array_klass()->element_type()->basic_type();
+  BasicType src_elem  = top_src->klass()->as_array_klass()->element_type()->basic_type();
   BasicType dest_elem = top_dest->klass()->as_array_klass()->element_type()->basic_type();
   if (src_elem  == T_ARRAY)  src_elem  = T_OBJECT;
   if (dest_elem == T_ARRAY)  dest_elem = T_OBJECT;
@@ -1232,6 +1239,13 @@
   }
   // This is where the memory effects are placed:
   const TypePtr* adr_type = TypeAryPtr::get_array_body_type(dest_elem);
+  if (ac->_dest_type != TypeOopPtr::BOTTOM) {
+    adr_type = ac->_dest_type->add_offset(Type::OffsetBot)->is_ptr();
+  }
+  if (ac->_src_type != ac->_dest_type) {
+    adr_type = TypeRawPtr::BOTTOM;
+  }
+
   generate_arraycopy(ac, alloc, &ctrl, merge_mem, &io,
                      adr_type, dest_elem,
                      src, src_offset, dest, dest_offset, length,
--- a/hotspot/src/share/vm/opto/matcher.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/matcher.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -83,6 +83,7 @@
   idealreg2spillmask  [Op_VecD] = NULL;
   idealreg2spillmask  [Op_VecX] = NULL;
   idealreg2spillmask  [Op_VecY] = NULL;
+  idealreg2spillmask  [Op_VecZ] = NULL;
 
   idealreg2debugmask  [Op_RegI] = NULL;
   idealreg2debugmask  [Op_RegN] = NULL;
@@ -94,6 +95,7 @@
   idealreg2debugmask  [Op_VecD] = NULL;
   idealreg2debugmask  [Op_VecX] = NULL;
   idealreg2debugmask  [Op_VecY] = NULL;
+  idealreg2debugmask  [Op_VecZ] = NULL;
 
   idealreg2mhdebugmask[Op_RegI] = NULL;
   idealreg2mhdebugmask[Op_RegN] = NULL;
@@ -105,6 +107,7 @@
   idealreg2mhdebugmask[Op_VecD] = NULL;
   idealreg2mhdebugmask[Op_VecX] = NULL;
   idealreg2mhdebugmask[Op_VecY] = NULL;
+  idealreg2mhdebugmask[Op_VecZ] = NULL;
 
   debug_only(_mem_node = NULL;)   // Ideal memory node consumed by mach node
 }
@@ -413,7 +416,7 @@
 void Matcher::init_first_stack_mask() {
 
   // Allocate storage for spill masks as masks for the appropriate load type.
-  RegMask *rms = (RegMask*)C->comp_arena()->Amalloc_D(sizeof(RegMask) * (3*6+4));
+  RegMask *rms = (RegMask*)C->comp_arena()->Amalloc_D(sizeof(RegMask) * (3*6+5));
 
   idealreg2spillmask  [Op_RegN] = &rms[0];
   idealreg2spillmask  [Op_RegI] = &rms[1];
@@ -440,6 +443,7 @@
   idealreg2spillmask  [Op_VecD] = &rms[19];
   idealreg2spillmask  [Op_VecX] = &rms[20];
   idealreg2spillmask  [Op_VecY] = &rms[21];
+  idealreg2spillmask  [Op_VecZ] = &rms[22];
 
   OptoReg::Name i;
 
@@ -524,6 +528,18 @@
     *idealreg2spillmask[Op_VecY] = *idealreg2regmask[Op_VecY];
      idealreg2spillmask[Op_VecY]->OR(aligned_stack_mask);
   }
+  if (Matcher::vector_size_supported(T_FLOAT,16)) {
+    // For VecZ we need enough alignment and 64 bytes (16 slots) for spills.
+    OptoReg::Name in = OptoReg::add(_in_arg_limit, -1);
+    for (int k = 1; (in >= init_in) && (k < RegMask::SlotsPerVecZ); k++) {
+      aligned_stack_mask.Remove(in);
+      in = OptoReg::add(in, -1);
+    }
+     aligned_stack_mask.clear_to_sets(RegMask::SlotsPerVecZ);
+     assert(aligned_stack_mask.is_AllStack(), "should be infinite stack");
+    *idealreg2spillmask[Op_VecZ] = *idealreg2regmask[Op_VecZ];
+     idealreg2spillmask[Op_VecZ]->OR(aligned_stack_mask);
+  }
    if (UseFPUForSpilling) {
      // This mask logic assumes that the spill operations are
      // symmetric and that the registers involved are the same size.
@@ -862,6 +878,10 @@
     MachNode *spillVectY = match_tree(new LoadVectorNode(NULL,mem,fp,atp,TypeVect::VECTY));
     idealreg2regmask[Op_VecY] = &spillVectY->out_RegMask();
   }
+  if (Matcher::vector_size_supported(T_FLOAT,16)) {
+    MachNode *spillVectZ = match_tree(new LoadVectorNode(NULL,mem,fp,atp,TypeVect::VECTZ));
+    idealreg2regmask[Op_VecZ] = &spillVectZ->out_RegMask();
+  }
 }
 
 #ifdef ASSERT
--- a/hotspot/src/share/vm/opto/memnode.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/memnode.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -28,6 +28,7 @@
 #include "memory/allocation.inline.hpp"
 #include "oops/objArrayKlass.hpp"
 #include "opto/addnode.hpp"
+#include "opto/arraycopynode.hpp"
 #include "opto/cfgnode.hpp"
 #include "opto/compile.hpp"
 #include "opto/connode.hpp"
@@ -107,6 +108,32 @@
 
 #endif
 
+static bool membar_for_arraycopy_helper(const TypeOopPtr *t_oop, MergeMemNode* mm, PhaseTransform *phase) {
+  if (mm->memory_at(Compile::AliasIdxRaw)->is_Proj()) {
+    Node* n = mm->memory_at(Compile::AliasIdxRaw)->in(0);
+    if ((n->is_ArrayCopy() && n->as_ArrayCopy()->may_modify(t_oop, phase)) ||
+        (n->is_CallLeaf() && n->as_CallLeaf()->may_modify(t_oop, phase))) {
+      return true;
+    }
+  }
+  return false;
+}
+
+static bool membar_for_arraycopy(const TypeOopPtr *t_oop, MemBarNode* mb, PhaseTransform *phase) {
+  Node* mem = mb->in(TypeFunc::Memory);
+  if (mem->is_MergeMem()) {
+    return membar_for_arraycopy_helper(t_oop, mem->as_MergeMem(), phase);
+  } else if (mem->is_Phi()) {
+    // after macro expansion of an ArrayCopyNode we may have a Phi
+    for (uint i = 1; i < mem->req(); i++) {
+      if (mem->in(i) != NULL && mem->in(i)->is_MergeMem() && membar_for_arraycopy_helper(t_oop, mem->in(i)->as_MergeMem(), phase)) {
+        return true;
+      }
+    }
+  }
+  return false;
+}
+
 Node *MemNode::optimize_simple_memory_chain(Node *mchain, const TypeOopPtr *t_oop, Node *load, PhaseGVN *phase) {
   assert((t_oop != NULL), "sanity");
   bool is_instance = t_oop->is_known_instance_field();
@@ -129,6 +156,7 @@
       if (proj_in->is_Allocate() && proj_in->_idx == instance_id) {
         break;  // hit one of our sentinels
       } else if (proj_in->is_Call()) {
+        // ArrayCopyNodes processed here as well
         CallNode *call = proj_in->as_Call();
         if (!call->may_modify(t_oop, phase)) { // returns false for instances
           result = call->in(TypeFunc::Memory);
@@ -136,7 +164,7 @@
       } else if (proj_in->is_Initialize()) {
         AllocateNode* alloc = proj_in->as_Initialize()->allocation();
         // Stop if this is the initialization for the object instance which
-        // which contains this memory slice, otherwise skip over it.
+        // contains this memory slice, otherwise skip over it.
         if ((alloc == NULL) || (alloc->_idx == instance_id)) {
           break;
         }
@@ -150,6 +178,9 @@
           }
         }
       } else if (proj_in->is_MemBar()) {
+        if (membar_for_arraycopy(t_oop, proj_in->as_MemBar(), phase)) {
+          break;
+        }
         result = proj_in->in(TypeFunc::Memory);
       } else {
         assert(false, "unexpected projection");
@@ -477,6 +508,75 @@
 }
 
 
+// Find an arraycopy that must have set (can_see_stored_value=true) or
+// could have set (can_see_stored_value=false) the value for this load
+Node* LoadNode::find_previous_arraycopy(PhaseTransform* phase, Node* ld_alloc, Node*& mem, bool can_see_stored_value) const {
+  if (mem->is_Proj() && mem->in(0) != NULL && (mem->in(0)->Opcode() == Op_MemBarStoreStore ||
+                                               mem->in(0)->Opcode() == Op_MemBarCPUOrder)) {
+    Node* mb = mem->in(0);
+    if (mb->in(0) != NULL && mb->in(0)->is_Proj() &&
+        mb->in(0)->in(0) != NULL && mb->in(0)->in(0)->is_ArrayCopy()) {
+      ArrayCopyNode* ac = mb->in(0)->in(0)->as_ArrayCopy();
+      if (ac->is_clonebasic()) {
+        intptr_t offset;
+        AllocateNode* alloc = AllocateNode::Ideal_allocation(ac->in(ArrayCopyNode::Dest), phase, offset);
+        assert(alloc != NULL && alloc->initialization()->is_complete_with_arraycopy(), "broken allocation");
+        if (alloc == ld_alloc) {
+          return ac;
+        }
+      }
+    }
+  } else if (mem->is_Proj() && mem->in(0) != NULL && mem->in(0)->is_ArrayCopy()) {
+    ArrayCopyNode* ac = mem->in(0)->as_ArrayCopy();
+
+    if (ac->is_arraycopy_validated() ||
+        ac->is_copyof_validated() ||
+        ac->is_copyofrange_validated()) {
+      Node* ld_addp = in(MemNode::Address);
+      if (ld_addp->is_AddP()) {
+        Node* ld_base = ld_addp->in(AddPNode::Address);
+        Node* ld_offs = ld_addp->in(AddPNode::Offset);
+
+        Node* dest = ac->in(ArrayCopyNode::Dest);
+
+        if (dest == ld_base) {
+          Node* src_pos = ac->in(ArrayCopyNode::SrcPos);
+          Node* dest_pos = ac->in(ArrayCopyNode::DestPos);
+          Node* len = ac->in(ArrayCopyNode::Length);
+
+          const TypeInt *dest_pos_t = phase->type(dest_pos)->isa_int();
+          const TypeX *ld_offs_t = phase->type(ld_offs)->isa_intptr_t();
+          const TypeInt *len_t = phase->type(len)->isa_int();
+          const TypeAryPtr* ary_t = phase->type(dest)->isa_aryptr();
+
+          if (dest_pos_t != NULL && ld_offs_t != NULL && len_t != NULL && ary_t != NULL) {
+            BasicType ary_elem  = ary_t->klass()->as_array_klass()->element_type()->basic_type();
+            uint header = arrayOopDesc::base_offset_in_bytes(ary_elem);
+            uint elemsize = type2aelembytes(ary_elem);
+
+            intptr_t dest_pos_plus_len_lo = (((intptr_t)dest_pos_t->_lo) + len_t->_lo) * elemsize + header;
+            intptr_t dest_pos_plus_len_hi = (((intptr_t)dest_pos_t->_hi) + len_t->_hi) * elemsize + header;
+            intptr_t dest_pos_lo = ((intptr_t)dest_pos_t->_lo) * elemsize + header;
+            intptr_t dest_pos_hi = ((intptr_t)dest_pos_t->_hi) * elemsize + header;
+
+            if (can_see_stored_value) {
+              if (ld_offs_t->_lo >= dest_pos_hi && ld_offs_t->_hi < dest_pos_plus_len_lo) {
+                return ac;
+              }
+            } else {
+              if (ld_offs_t->_hi < dest_pos_lo || ld_offs_t->_lo >= dest_pos_plus_len_hi) {
+                mem = ac->in(TypeFunc::Memory);
+              }
+              return ac;
+            }
+          }
+        }
+      }
+    }
+  }
+  return NULL;
+}
+
 // The logic for reordering loads and stores uses four steps:
 // (a) Walk carefully past stores and initializations which we
 //     can prove are independent of this load.
@@ -510,6 +610,7 @@
   for (;;) {                // While we can dance past unrelated stores...
     if (--cnt < 0)  break;  // Caught in cycle or a complicated dance?
 
+    Node* prev = mem;
     if (mem->is_Store()) {
       Node* st_adr = mem->in(MemNode::Address);
       intptr_t st_offset = 0;
@@ -580,15 +681,26 @@
         return mem;         // let caller handle steps (c), (d)
       }
 
+    } else if (find_previous_arraycopy(phase, alloc, mem, false) != NULL) {
+      if (prev != mem) {
+        // Found an arraycopy but it doesn't affect that load
+        continue;
+      }
+      // Found an arraycopy that may affect that load
+      return mem;
     } else if (addr_t != NULL && addr_t->is_known_instance_field()) {
       // Can't use optimize_simple_memory_chain() since it needs PhaseGVN.
       if (mem->is_Proj() && mem->in(0)->is_Call()) {
+        // ArrayCopyNodes processed here as well.
         CallNode *call = mem->in(0)->as_Call();
         if (!call->may_modify(addr_t, phase)) {
           mem = call->in(TypeFunc::Memory);
           continue;         // (a) advance through independent call memory
         }
       } else if (mem->is_Proj() && mem->in(0)->is_MemBar()) {
+        if (membar_for_arraycopy(addr_t, mem->in(0)->as_MemBar(), phase)) {
+          break;
+        }
         mem = mem->in(0)->in(TypeFunc::Memory);
         continue;           // (a) advance through independent MemBar memory
       } else if (mem->is_ClearArray()) {
@@ -760,6 +872,66 @@
   return false;
 }
 
+// Is the value loaded previously stored by an arraycopy? If so return
+// a load node that reads from the source array so we may be able to
+// optimize out the ArrayCopy node later.
+Node* MemNode::can_see_arraycopy_value(Node* st, PhaseTransform* phase) const {
+  Node* ld_adr = in(MemNode::Address);
+  intptr_t ld_off = 0;
+  AllocateNode* ld_alloc = AllocateNode::Ideal_allocation(ld_adr, phase, ld_off);
+  Node* ac = find_previous_arraycopy(phase, ld_alloc, st, true);
+  if (ac != NULL) {
+    assert(ac->is_ArrayCopy(), "what kind of node can this be?");
+    assert(is_Load(), "only for loads");
+
+    if (ac->as_ArrayCopy()->is_clonebasic()) {
+      assert(ld_alloc != NULL, "need an alloc");
+      Node* ld = clone();
+      Node* addp = in(MemNode::Address)->clone();
+      assert(addp->is_AddP(), "address must be addp");
+      assert(addp->in(AddPNode::Base) == ac->in(ArrayCopyNode::Dest)->in(AddPNode::Base), "strange pattern");
+      assert(addp->in(AddPNode::Address) == ac->in(ArrayCopyNode::Dest)->in(AddPNode::Address), "strange pattern");
+      addp->set_req(AddPNode::Base, ac->in(ArrayCopyNode::Src)->in(AddPNode::Base));
+      addp->set_req(AddPNode::Address, ac->in(ArrayCopyNode::Src)->in(AddPNode::Address));
+      ld->set_req(MemNode::Address, phase->transform(addp));
+      if (in(0) != NULL) {
+        assert(ld_alloc->in(0) != NULL, "alloc must have control");
+        ld->set_req(0, ld_alloc->in(0));
+      }
+      return ld;
+    } else {
+      Node* ld = clone();
+      Node* addp = in(MemNode::Address)->clone();
+      assert(addp->in(AddPNode::Base) == addp->in(AddPNode::Address), "should be");
+      addp->set_req(AddPNode::Base, ac->in(ArrayCopyNode::Src));
+      addp->set_req(AddPNode::Address, ac->in(ArrayCopyNode::Src));
+
+      const TypeAryPtr* ary_t = phase->type(in(MemNode::Address))->isa_aryptr();
+      BasicType ary_elem  = ary_t->klass()->as_array_klass()->element_type()->basic_type();
+      uint header = arrayOopDesc::base_offset_in_bytes(ary_elem);
+      uint shift  = exact_log2(type2aelembytes(ary_elem));
+
+      Node* diff = phase->transform(new SubINode(ac->in(ArrayCopyNode::SrcPos), ac->in(ArrayCopyNode::DestPos)));
+#ifdef _LP64
+      diff = phase->transform(new ConvI2LNode(diff));
+#endif
+      diff = phase->transform(new LShiftXNode(diff, phase->intcon(shift)));
+
+      Node* offset = phase->transform(new AddXNode(addp->in(AddPNode::Offset), diff));
+      addp->set_req(AddPNode::Offset, offset);
+      ld->set_req(MemNode::Address, phase->transform(addp));
+
+      if (in(0) != NULL) {
+        assert(ac->in(0) != NULL, "alloc must have control");
+        ld->set_req(0, ac->in(0));
+      }
+      return ld;
+    }
+  }
+  return NULL;
+}
+
+
 //---------------------------can_see_stored_value------------------------------
 // This routine exists to make sure this set of tests is done the same
 // everywhere.  We need to make a coordinated change: first LoadNode::Ideal
@@ -793,6 +965,7 @@
           opc == Op_MemBarRelease ||
           opc == Op_StoreFence ||
           opc == Op_MemBarReleaseLock ||
+          opc == Op_MemBarStoreStore ||
           opc == Op_MemBarCPUOrder) {
         Node* mem = current->in(0)->in(TypeFunc::Memory);
         if (mem->is_MergeMem()) {
@@ -863,8 +1036,9 @@
       if ((alloc != NULL) && (alloc == ld_alloc)) {
         // examine a captured store value
         st = init->find_captured_store(ld_off, memory_size(), phase);
-        if (st != NULL)
+        if (st != NULL) {
           continue;             // take one more trip around
+        }
       }
     }
 
@@ -1335,6 +1509,29 @@
     }
   }
 
+  // Is there a dominating load that loads the same value?  Leave
+  // anything that is not a load of a field/array element (like
+  // barriers etc.) alone
+  if (in(0) != NULL && adr_type() != TypeRawPtr::BOTTOM && can_reshape) {
+    for (DUIterator_Fast imax, i = mem->fast_outs(imax); i < imax; i++) {
+      Node *use = mem->fast_out(i);
+      if (use != this &&
+          use->Opcode() == Opcode() &&
+          use->in(0) != NULL &&
+          use->in(0) != in(0) &&
+          use->in(Address) == in(Address)) {
+        Node* ctl = in(0);
+        for (int i = 0; i < 10 && ctl != NULL; i++) {
+          ctl = IfNode::up_one_dom(ctl);
+          if (ctl == use->in(0)) {
+            set_req(0, use->in(0));
+            return this;
+          }
+        }
+      }
+    }
+  }
+
   // Check for prior store with a different base or offset; make Load
   // independent.  Skip through any number of them.  Bail out if the stores
   // are in an endless dead cycle and report no progress.  This is a key
@@ -1348,6 +1545,12 @@
   // the alias index stuff.  So instead, peek through Stores and IFF we can
   // fold up, do so.
   Node* prev_mem = find_previous_store(phase);
+  if (prev_mem != NULL) {
+    Node* value = can_see_arraycopy_value(prev_mem, phase);
+    if (value != NULL) {
+      return value;
+    }
+  }
   // Steps (a), (b):  Walk past independent stores to find an exact match.
   if (prev_mem != NULL && prev_mem != in(MemNode::Memory)) {
     // (c) See if we can fold up on the spot, but don't fold up here.
@@ -2529,7 +2732,6 @@
 
 //=============================================================================
 //-------------------------------adr_type--------------------------------------
-// Do we Match on this edge index or not?  Do not match memory
 const TypePtr* ClearArrayNode::adr_type() const {
   Node *adr = in(3);
   if (adr == NULL)  return NULL; // node is dead
--- a/hotspot/src/share/vm/opto/memnode.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/memnode.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -72,6 +72,8 @@
     debug_only(_adr_type=at; adr_type();)
   }
 
+  virtual Node* find_previous_arraycopy(PhaseTransform* phase, Node* ld_alloc, Node*& mem, bool can_see_stored_value) const { return NULL; }
+
 public:
   // Helpers for the optimizer.  Documented in memnode.cpp.
   static bool detect_ptr_independence(Node* p1, AllocateNode* a1,
@@ -124,6 +126,7 @@
   // Can this node (load or store) accurately see a stored value in
   // the given memory state?  (The state may or may not be in(Memory).)
   Node* can_see_stored_value(Node* st, PhaseTransform* phase) const;
+  Node* can_see_arraycopy_value(Node* st, PhaseTransform* phase) const;
 
 #ifndef PRODUCT
   static void dump_adr_type(const Node* mem, const TypePtr* adr_type, outputStream *st);
@@ -147,6 +150,8 @@
   // Should LoadNode::Ideal() attempt to remove control edges?
   virtual bool can_remove_control() const;
   const Type* const _type;      // What kind of value is loaded?
+
+  virtual Node* find_previous_arraycopy(PhaseTransform* phase, Node* ld_alloc, Node*& mem, bool can_see_stored_value) const;
 public:
 
   LoadNode(Node *c, Node *mem, Node *adr, const TypePtr* at, const Type *rt, MemOrd mo)
--- a/hotspot/src/share/vm/opto/node.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/node.cpp	Wed Jul 05 20:35:10 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
@@ -1658,6 +1658,9 @@
     return;                     // don't process dead nodes
   }
 
+  if (C->clone_map().value(_idx) != 0) {
+    C->clone_map().dump(_idx);
+  }
   // Dump node-specific info
   dump_spec(st);
 #ifdef ASSERT
--- a/hotspot/src/share/vm/opto/opcodes.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/opcodes.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -42,6 +42,7 @@
   "VecD",
   "VecX",
   "VecY",
+  "VecZ",
   "_last_machine_leaf",
 #include "classes.hpp"
   "_last_class_name",
--- a/hotspot/src/share/vm/opto/opcodes.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/opcodes.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -40,6 +40,7 @@
   macro(VecD)                   // Machine vectord register
   macro(VecX)                   // Machine vectorx register
   macro(VecY)                   // Machine vectory register
+  macro(VecZ)                   // Machine vectorz register
   macro(RegFlags)               // Machine flags   register
   _last_machine_leaf,           // Split between regular opcodes and machine
 #include "classes.hpp"
--- a/hotspot/src/share/vm/opto/optoreg.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/optoreg.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -103,6 +103,10 @@
     return r - stack0();
   }
 
+  static void invalidate(Name n) {
+    vm2opto[n] = Bad;
+  }
+
   // convert a stack slot number into an OptoReg::Name
   static OptoReg::Name stack2reg( int idx) {
     return Name(stack0() + idx);
--- a/hotspot/src/share/vm/opto/output.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/output.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1880,8 +1880,8 @@
   if (!do_scheduling())
     return;
 
-  // Scheduling code works only with pairs (8 bytes) maximum.
-  if (max_vector_size() > 8)
+  // Scheduling code works only with pairs (16 bytes) maximum.
+  if (max_vector_size() > 16)
     return;
 
   TracePhase tp("isched", &timers[_t_instrSched]);
--- a/hotspot/src/share/vm/opto/regmask.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/regmask.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -114,11 +114,14 @@
 
 //=============================================================================
 bool RegMask::is_vector(uint ireg) {
-  return (ireg == Op_VecS || ireg == Op_VecD || ireg == Op_VecX || ireg == Op_VecY);
+  return (ireg == Op_VecS || ireg == Op_VecD ||
+          ireg == Op_VecX || ireg == Op_VecY || ireg == Op_VecZ );
 }
 
 int RegMask::num_registers(uint ireg) {
     switch(ireg) {
+      case Op_VecZ:
+        return 16;
       case Op_VecY:
         return 8;
       case Op_VecX:
@@ -233,7 +236,8 @@
   return true;
 }
 
-static int low_bits[3] = { 0x55555555, 0x11111111, 0x01010101 };
+// only indicies of power 2 are accessed, so index 3 is only filled in for storage.
+static int low_bits[5] = { 0x55555555, 0x11111111, 0x01010101, 0x00000000, 0x00010001 };
 //------------------------------find_first_set---------------------------------
 // Find the lowest-numbered register set in the mask.  Return the
 // HIGHEST register number in the set, or BAD if no sets.
@@ -254,7 +258,7 @@
 // Clear out partial bits; leave only aligned adjacent bit pairs
 void RegMask::clear_to_sets(const int size) {
   if (size == 1) return;
-  assert(2 <= size && size <= 8, "update low bits table");
+  assert(2 <= size && size <= 16, "update low bits table");
   assert(is_power_of_2(size), "sanity");
   int low_bits_mask = low_bits[size>>2];
   for (int i = 0; i < RM_SIZE; i++) {
@@ -268,6 +272,9 @@
       sets |= (sets>>2);         // Smear 2 hi-bits into a set
       if (size > 4) {
         sets |= (sets>>4);       // Smear 4 hi-bits into a set
+        if (size > 8) {
+          sets |= (sets>>8);     // Smear 8 hi-bits into a set
+        }
       }
     }
     _A[i] = sets;
@@ -279,7 +286,7 @@
 // Smear out partial bits to aligned adjacent bit sets
 void RegMask::smear_to_sets(const int size) {
   if (size == 1) return;
-  assert(2 <= size && size <= 8, "update low bits table");
+  assert(2 <= size && size <= 16, "update low bits table");
   assert(is_power_of_2(size), "sanity");
   int low_bits_mask = low_bits[size>>2];
   for (int i = 0; i < RM_SIZE; i++) {
@@ -294,6 +301,9 @@
       sets |= (sets<<2);         // Smear 2 lo-bits into a set
       if (size > 4) {
         sets |= (sets<<4);       // Smear 4 lo-bits into a set
+        if (size > 8) {
+          sets |= (sets<<8);     // Smear 8 lo-bits into a set
+        }
       }
     }
     _A[i] = sets;
@@ -304,7 +314,7 @@
 //------------------------------is_aligned_set--------------------------------
 bool RegMask::is_aligned_sets(const int size) const {
   if (size == 1) return true;
-  assert(2 <= size && size <= 8, "update low bits table");
+  assert(2 <= size && size <= 16, "update low bits table");
   assert(is_power_of_2(size), "sanity");
   int low_bits_mask = low_bits[size>>2];
   // Assert that the register mask contains only bit sets.
@@ -330,7 +340,7 @@
 // Works also for size 1.
 int RegMask::is_bound_set(const int size) const {
   if( is_AllStack() ) return false;
-  assert(1 <= size && size <= 8, "update low bits table");
+  assert(1 <= size && size <= 16, "update low bits table");
   int bit = -1;                 // Set to hold the one bit allowed
   for (int i = 0; i < RM_SIZE; i++) {
     if (_A[i] ) {               // Found some bits
@@ -346,10 +356,12 @@
         if (((-1) & ~(bit-1)) != _A[i])
           return false;         // Found many bits, so fail
         i++;                    // Skip iteration forward and check high part
-        // The lower 24 bits should be 0 since it is split case and size <= 8.
-        int set = bit>>24;
+        // The lower (32-size) bits should be 0 since it is split case.
+        int clear_bit_size = 32-size;
+        int shift_back_size = 32-clear_bit_size;
+        int set = bit>>clear_bit_size;
         set = set & -set; // Remove sign extension.
-        set = (((set << size) - 1) >> 8);
+        set = (((set << size) - 1) >> shift_back_size);
         if (i >= RM_SIZE || _A[i] != set)
           return false; // Require expected low bits in next word
       }
@@ -375,7 +387,7 @@
 //------------------------------Size-------------------------------------------
 // Compute size of register mask in bits
 uint RegMask::Size() const {
-  extern uint8_t bitsInByte[256];
+  extern uint8_t bitsInByte[512];
   uint sum = 0;
   for( int i = 0; i < RM_SIZE; i++ )
     sum +=
--- a/hotspot/src/share/vm/opto/regmask.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/regmask.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -98,7 +98,8 @@
          SlotsPerVecS = 1,
          SlotsPerVecD = 2,
          SlotsPerVecX = 4,
-         SlotsPerVecY = 8 };
+         SlotsPerVecY = 8,
+         SlotsPerVecZ = 16 };
 
   // A constructor only used by the ADLC output.  All mask fields are filled
   // in directly.  Calls to this look something like RM(1,2,3,4);
@@ -299,13 +300,13 @@
   static bool can_represent(OptoReg::Name reg) {
     // NOTE: -1 in computation reflects the usage of the last
     //       bit of the regmask as an infinite stack flag and
-    //       -7 is to keep mask aligned for largest value (VecY).
+    //       -7 is to keep mask aligned for largest value (VecZ).
     return (int)reg < (int)(CHUNK_SIZE-1);
   }
   static bool can_represent_arg(OptoReg::Name reg) {
-    // NOTE: -SlotsPerVecY in computation reflects the need
-    //       to keep mask aligned for largest value (VecY).
-    return (int)reg < (int)(CHUNK_SIZE-SlotsPerVecY);
+    // NOTE: -SlotsPerVecZ in computation reflects the need
+    //       to keep mask aligned for largest value (VecZ).
+    return (int)reg < (int)(CHUNK_SIZE-SlotsPerVecZ);
   }
 };
 
--- a/hotspot/src/share/vm/opto/superword.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/superword.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2007, 2014, 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
@@ -54,6 +54,7 @@
   _mem_slice_head(arena(), 8,  0, NULL),  // memory slice heads
   _mem_slice_tail(arena(), 8,  0, NULL),  // memory slice tails
   _node_info(arena(), 8,  0, SWNodeInfo::initial), // info needed per node
+  _clone_map(phase->C->clone_map()),      // map of nodes created in cloning
   _align_to_ref(NULL),                    // memory reference to align vectors to
   _disjoint_ptrs(arena(), 8,  0, OrderedPair::initial), // runtime disambiguated pointer pairs
   _dg(_arena),                            // dependence graph
@@ -66,7 +67,14 @@
   _lp(NULL),                              // LoopNode
   _bb(NULL),                              // basic block
   _iv(NULL),                              // induction var
-  _race_possible(false)                   // cases where SDMU is true
+  _race_possible(false),                  // cases where SDMU is true
+  _num_work_vecs(0),                      // amount of vector work we have
+  _num_reductions(0),                     // amount of reduction work we have
+  _do_vector_loop(phase->C->do_vector_loop()),  // whether to do vectorization/simd style
+  _ii_first(-1),                          // first loop generation index - only if do_vector_loop()
+  _ii_last(-1),                           // last loop generation index - only if do_vector_loop()
+  _ii_order(arena(), 8, 0, 0),
+  _vector_loop_debug(phase->C->has_method() && phase->C->method_has_option("VectorizeDebug"))
 {}
 
 //------------------------------transform_loop---------------------------
@@ -145,14 +153,53 @@
 //
 void SuperWord::SLP_extract() {
 
+#ifndef PRODUCT
+  if (_do_vector_loop && TraceSuperWord) {
+    tty->print("SuperWord::SLP_extract\n");
+    tty->print("input loop\n");
+    _lpt->dump_head();
+    _lpt->dump();
+    for (uint i = 0; i < _lpt->_body.size(); i++) {
+      _lpt->_body.at(i)->dump();
+    }
+  }
+#endif
   // Ready the block
-  if (!construct_bb())
+  if (!construct_bb()) {
     return; // Exit if no interesting nodes or complex graph.
-
+  }
+  // build    _dg, _disjoint_ptrs
   dependence_graph();
 
+  // compute function depth(Node*)
   compute_max_depth();
 
+  if (_do_vector_loop) {
+    if (mark_generations() != -1) {
+      hoist_loads_in_graph(); // this only rebuild the graph; all basic structs need rebuild explicitly
+
+      if (!construct_bb()) {
+        return; // Exit if no interesting nodes or complex graph.
+      }
+      dependence_graph();
+      compute_max_depth();
+    }
+
+#ifndef PRODUCT
+    if (TraceSuperWord) {
+      tty->print_cr("\nSuperWord::_do_vector_loop: graph after hoist_loads_in_graph");
+      _lpt->dump_head();
+      for (int j = 0; j < _block.length(); j++) {
+        Node* n = _block.at(j);
+        int d = depth(n);
+        for (int i = 0;  i < d; i++) tty->print("%s", "  ");
+        tty->print("%d :", d);
+        n->dump();
+      }
+    }
+#endif
+  }
+
   compute_vector_element_type();
 
   // Attempt vectorization
@@ -161,6 +208,17 @@
 
   extend_packlist();
 
+  if (_do_vector_loop) {
+    if (_packset.length() == 0) {
+#ifndef PRODUCT
+      if (TraceSuperWord) {
+        tty->print_cr("\nSuperWord::_do_vector_loop DFA could not build packset, now trying to build anyway");
+      }
+#endif
+      pack_parallel();
+    }
+  }
+
   combine_packs();
 
   construct_my_pack_map();
@@ -226,7 +284,7 @@
     // Create initial pack pairs of memory operations for which
     // alignment is set and vectors will be aligned.
     bool create_pack = true;
-    if (memory_alignment(mem_ref, best_iv_adjustment) == 0) {
+    if (memory_alignment(mem_ref, best_iv_adjustment) == 0 || _do_vector_loop) {
       if (!Matcher::misaligned_vectors_ok()) {
         int vw = vector_width(mem_ref);
         int vw_best = vector_width(best_align_to_mem_ref);
@@ -235,6 +293,13 @@
           // if unaligned memory access is not allowed because number of
           // iterations in pre-loop will be not enough to align it.
           create_pack = false;
+        } else {
+          SWPointer p2(best_align_to_mem_ref, this);
+          if (align_to_ref_p.invar() != p2.invar()) {
+            // Do not vectorize memory accesses with different invariants
+            // if unaligned memory accesses are not allowed.
+            create_pack = false;
+          }
         }
       }
     } else {
@@ -272,7 +337,9 @@
               Node_List* pair = new Node_List();
               pair->push(s1);
               pair->push(s2);
-              _packset.append(pair);
+              if (!_do_vector_loop || _clone_map.idx(s1->_idx) == _clone_map.idx(s2->_idx)) {
+                _packset.append(pair);
+              }
             }
           }
         }
@@ -417,7 +484,7 @@
 
 #ifdef ASSERT
   if (TraceSuperWord && Verbose) {
-    tty->print_cr("\nVector memops after find_align_to_refs");
+    tty->print_cr("\nVector memops after find_align_to_ref");
     for (uint i = 0; i < memops.size(); i++) {
       MemNode* s = memops.at(i)->as_Mem();
       s->dump();
@@ -456,24 +523,50 @@
   if (ABS(span) == mem_size && (ABS(offset) % mem_size) == 0) {
     return true;
   }
-  // If initial offset from start of object is computable,
-  // compute alignment within the vector.
+  // If the initial offset from start of the object is computable,
+  // check if the pre-loop can align the final offset accordingly.
+  //
+  // In other words: Can we find an i such that the offset
+  // after i pre-loop iterations is aligned to vw?
+  //   (init_offset + pre_loop) % vw == 0              (1)
+  // where
+  //   pre_loop = i * span
+  // is the number of bytes added to the offset by i pre-loop iterations.
+  //
+  // For this to hold we need pre_loop to increase init_offset by
+  //   pre_loop = vw - (init_offset % vw)
+  //
+  // This is only possible if pre_loop is divisible by span because each
+  // pre-loop iteration increases the initial offset by 'span' bytes:
+  //   (vw - (init_offset % vw)) % span == 0
+  //
   int vw = vector_width_in_bytes(p.mem());
   assert(vw > 1, "sanity");
-  if (vw % span == 0) {
-    Node* init_nd = pre_end->init_trip();
-    if (init_nd->is_Con() && p.invar() == NULL) {
-      int init = init_nd->bottom_type()->is_int()->get_con();
-
-      int init_offset = init * p.scale_in_bytes() + offset;
-      assert(init_offset >= 0, "positive offset from object start");
-
+  Node* init_nd = pre_end->init_trip();
+  if (init_nd->is_Con() && p.invar() == NULL) {
+    int init = init_nd->bottom_type()->is_int()->get_con();
+    int init_offset = init * p.scale_in_bytes() + offset;
+    assert(init_offset >= 0, "positive offset from object start");
+    if (vw % span == 0) {
+      // If vm is a multiple of span, we use formula (1).
       if (span > 0) {
         return (vw - (init_offset % vw)) % span == 0;
       } else {
         assert(span < 0, "nonzero stride * scale");
         return (init_offset % vw) % -span == 0;
       }
+    } else if (span % vw == 0) {
+      // If span is a multiple of vw, we can simplify formula (1) to:
+      //   (init_offset + i * span) % vw == 0
+      //     =>
+      //   (init_offset % vw) + ((i * span) % vw) == 0
+      //     =>
+      //   init_offset % vw == 0
+      //
+      // Because we add a multiple of vw to the initial offset, the final
+      // offset is a multiple of vw if and only if init_offset is a multiple.
+      //
+      return (init_offset % vw) == 0;
     }
   }
   return false;
@@ -485,17 +578,23 @@
   SWPointer align_to_ref_p(mem_ref, this);
   int offset = align_to_ref_p.offset_in_bytes();
   int scale  = align_to_ref_p.scale_in_bytes();
+  int elt_size = align_to_ref_p.memory_size();
   int vw       = vector_width_in_bytes(mem_ref);
   assert(vw > 1, "sanity");
-  int stride_sign   = (scale * iv_stride()) > 0 ? 1 : -1;
-  // At least one iteration is executed in pre-loop by default. As result
-  // several iterations are needed to align memory operations in main-loop even
-  // if offset is 0.
-  int iv_adjustment_in_bytes = (stride_sign * vw - (offset % vw));
-  int elt_size = align_to_ref_p.memory_size();
-  assert(((ABS(iv_adjustment_in_bytes) % elt_size) == 0),
-         err_msg_res("(%d) should be divisible by (%d)", iv_adjustment_in_bytes, elt_size));
-  int iv_adjustment = iv_adjustment_in_bytes/elt_size;
+  int iv_adjustment;
+  if (scale != 0) {
+    int stride_sign = (scale * iv_stride()) > 0 ? 1 : -1;
+    // At least one iteration is executed in pre-loop by default. As result
+    // several iterations are needed to align memory operations in main-loop even
+    // if offset is 0.
+    int iv_adjustment_in_bytes = (stride_sign * vw - (offset % vw));
+    assert(((ABS(iv_adjustment_in_bytes) % elt_size) == 0),
+           err_msg_res("(%d) should be divisible by (%d)", iv_adjustment_in_bytes, elt_size));
+    iv_adjustment = iv_adjustment_in_bytes/elt_size;
+  } else {
+    // This memory op is not dependent on iv (scale == 0)
+    iv_adjustment = 0;
+  }
 
 #ifndef PRODUCT
   if (TraceSuperWord)
@@ -526,6 +625,14 @@
     // Get slice in predecessor order (last is first)
     mem_slice_preds(n_tail, n, _nlist);
 
+#ifndef PRODUCT
+    if(TraceSuperWord && Verbose) {
+      tty->print_cr("SuperWord::dependence_graph: built a new mem slice");
+      for (int j = _nlist.length() - 1; j >= 0 ; j--) {
+        _nlist.at(j)->dump();
+      }
+    }
+#endif
     // Make the slice dependent on the root
     DepMem* slice = _dg.dep(n);
     _dg.make_edge(_dg.root(), slice);
@@ -1112,7 +1219,6 @@
 //------------------------------filter_packs---------------------------
 // Remove packs that are not implemented or not profitable.
 void SuperWord::filter_packs() {
-
   // Remove packs that are not implemented
   for (int i = _packset.length() - 1; i >= 0; i--) {
     Node_List* pk = _packset.at(i);
@@ -1126,6 +1232,12 @@
 #endif
       remove_pack_at(i);
     }
+    Node *n = pk->at(0);
+    if (n->is_reduction()) {
+      _num_reductions++;
+    } else {
+      _num_work_vecs++;
+    }
   }
 
   // Remove packs that are not profitable
@@ -1167,7 +1279,12 @@
     uint size = p->size();
     if (p0->is_reduction()) {
       const Type *arith_type = p0->bottom_type();
-      retValue = ReductionNode::implemented(opc, size, arith_type->basic_type());
+      // Length 2 reductions of INT/LONG do not offer performance benefits
+      if (((arith_type->basic_type() == T_INT) || (arith_type->basic_type() == T_LONG)) && (size == 2)) {
+        retValue = false;
+      } else {
+        retValue = ReductionNode::implemented(opc, size, arith_type->basic_type());
+      }
     } else {
       retValue = VectorNode::implemented(opc, size, velt_basic_type(p0));
     }
@@ -1210,8 +1327,9 @@
   if (p0->is_reduction()) {
     Node* second_in = p0->in(2);
     Node_List* second_pk = my_pack(second_in);
-    if (second_pk == NULL) {
-      // Remove reduction flag if no parent pack, it is not profitable
+    if ((second_pk == NULL) || (_num_work_vecs == _num_reductions)) {
+      // Remove reduction flag if no parent pack or if not enough work
+      // to cover reduction expansion overhead
       p0->remove_flag(Node::Flag_is_reduction);
       return false;
     } else if (second_pk->size() != p->size()) {
@@ -2349,12 +2467,29 @@
   _data_entry.clear();
   _mem_slice_head.clear();
   _mem_slice_tail.clear();
+  _iteration_first.clear();
+  _iteration_last.clear();
   _node_info.clear();
   _align_to_ref = NULL;
   _lpt = NULL;
   _lp = NULL;
   _bb = NULL;
   _iv = NULL;
+  _race_possible = 0;
+  _num_work_vecs = 0;
+  _num_reductions = 0;
+}
+
+//------------------------------restart---------------------------
+void SuperWord::restart() {
+  _dg.init();
+  _packset.clear();
+  _disjoint_ptrs.clear();
+  _block.clear();
+  _data_entry.clear();
+  _mem_slice_head.clear();
+  _mem_slice_tail.clear();
+  _node_info.clear();
 }
 
 //------------------------------print_packset---------------------------
@@ -2422,6 +2557,11 @@
   }
   // Match AddP(base, AddP(ptr, k*iv [+ invariant]), constant)
   Node* base = adr->in(AddPNode::Base);
+  // The base address should be loop invariant
+  if (!invariant(base)) {
+    assert(!valid(), "base address is loop variant");
+    return;
+  }
   //unsafe reference could not be aligned appropriately without runtime checking
   if (base == NULL || base->bottom_type() == Type::TOP) {
     assert(!valid(), "unsafe access");
@@ -2734,3 +2874,401 @@
     _done = true;
   }
 }
+
+//
+// --------------------------------- vectorization/simd -----------------------------------
+//
+Node*  SuperWord::find_phi_for_mem_dep(LoadNode* ld) {
+  assert(in_bb(ld), "must be in block");
+  if (_clone_map.gen(ld->_idx) == _ii_first) {
+#ifndef PRODUCT
+    if (_vector_loop_debug) {
+      tty->print_cr("SuperWord::find_phi_for_mem_dep _clone_map.gen(ld->_idx)=%d",
+                    _clone_map.gen(ld->_idx));
+    }
+#endif
+    return NULL; //we think that any ld in the first gen being vectorizable
+  }
+
+  Node* mem = ld->in(MemNode::Memory);
+  if (mem->outcnt() <= 1) {
+    // we don't want to remove the only edge from mem node to load
+#ifndef PRODUCT
+    if (_vector_loop_debug) {
+      tty->print_cr("SuperWord::find_phi_for_mem_dep input node %d to load %d has no other outputs and edge mem->load cannot be removed",
+                    mem->_idx, ld->_idx);
+      ld->dump();
+      mem->dump();
+    }
+#endif
+    return NULL;
+  }
+  if (!in_bb(mem) || _clone_map.gen(mem->_idx) == _clone_map.gen(ld->_idx)) {
+#ifndef PRODUCT
+    if (_vector_loop_debug) {
+      tty->print_cr("SuperWord::find_phi_for_mem_dep _clone_map.gen(mem->_idx)=%d",
+                    _clone_map.gen(mem->_idx));
+    }
+#endif
+    return NULL; // does not depend on loop volatile node or depends on the same generation
+  }
+
+  //otherwise first node should depend on mem-phi
+  Node* first = first_node(ld);
+  assert(first->is_Load(), "must be Load");
+  Node* phi = first->as_Load()->in(MemNode::Memory);
+  if (!phi->is_Phi() || phi->bottom_type() != Type::MEMORY) {
+#ifndef PRODUCT
+    if (_vector_loop_debug) {
+      tty->print_cr("SuperWord::find_phi_for_mem_dep load is not vectorizable node, since it's `first` does not take input from mem phi");
+      ld->dump();
+      first->dump();
+    }
+#endif
+    return NULL;
+  }
+
+  Node* tail = 0;
+  for (int m = 0; m < _mem_slice_head.length(); m++) {
+    if (_mem_slice_head.at(m) == phi) {
+      tail = _mem_slice_tail.at(m);
+    }
+  }
+  if (tail == 0) { //test that found phi is in the list  _mem_slice_head
+#ifndef PRODUCT
+    if (_vector_loop_debug) {
+      tty->print_cr("SuperWord::find_phi_for_mem_dep load %d is not vectorizable node, its phi %d is not _mem_slice_head",
+                    ld->_idx, phi->_idx);
+      ld->dump();
+      phi->dump();
+    }
+#endif
+    return NULL;
+  }
+
+  // now all conditions are met
+  return phi;
+}
+
+Node* SuperWord::first_node(Node* nd) {
+  for (int ii = 0; ii < _iteration_first.length(); ii++) {
+    Node* nnn = _iteration_first.at(ii);
+    if (_clone_map.idx(nnn->_idx) == _clone_map.idx(nd->_idx)) {
+#ifndef PRODUCT
+      if (_vector_loop_debug) {
+        tty->print_cr("SuperWord::first_node: %d is the first iteration node for %d (_clone_map.idx(nnn->_idx) = %d)",
+                      nnn->_idx, nd->_idx, _clone_map.idx(nnn->_idx));
+      }
+#endif
+      return nnn;
+    }
+  }
+
+#ifndef PRODUCT
+  if (_vector_loop_debug) {
+    tty->print_cr("SuperWord::first_node: did not find first iteration node for %d (_clone_map.idx(nd->_idx)=%d)",
+                  nd->_idx, _clone_map.idx(nd->_idx));
+  }
+#endif
+  return 0;
+}
+
+Node* SuperWord::last_node(Node* nd) {
+  for (int ii = 0; ii < _iteration_last.length(); ii++) {
+    Node* nnn = _iteration_last.at(ii);
+    if (_clone_map.idx(nnn->_idx) == _clone_map.idx(nd->_idx)) {
+#ifndef PRODUCT
+      if (_vector_loop_debug) {
+        tty->print_cr("SuperWord::last_node _clone_map.idx(nnn->_idx)=%d, _clone_map.idx(nd->_idx)=%d",
+                      _clone_map.idx(nnn->_idx), _clone_map.idx(nd->_idx));
+      }
+#endif
+      return nnn;
+    }
+  }
+  return 0;
+}
+
+int SuperWord::mark_generations() {
+  Node *ii_err = 0, *tail_err;
+  for (int i = 0; i < _mem_slice_head.length(); i++) {
+    Node* phi  = _mem_slice_head.at(i);
+    assert(phi->is_Phi(), "must be phi");
+
+    Node* tail = _mem_slice_tail.at(i);
+    if (_ii_last == -1) {
+      tail_err = tail;
+      _ii_last = _clone_map.gen(tail->_idx);
+    }
+    else if (_ii_last != _clone_map.gen(tail->_idx)) {
+#ifndef PRODUCT
+      if (TraceSuperWord && Verbose) {
+        tty->print_cr("SuperWord::mark_generations _ii_last error - found different generations in two tail nodes ");
+        tail->dump();
+        tail_err->dump();
+      }
+#endif
+      return -1;
+    }
+
+    // find first iteration in the loop
+    for (DUIterator_Fast imax, i = phi->fast_outs(imax); i < imax; i++) {
+      Node* ii = phi->fast_out(i);
+      if (in_bb(ii) && ii->is_Store()) { // we speculate that normally Stores of one and one only generation have deps from mem phi
+        if (_ii_first == -1) {
+          ii_err = ii;
+          _ii_first = _clone_map.gen(ii->_idx);
+        } else if (_ii_first != _clone_map.gen(ii->_idx)) {
+#ifndef PRODUCT
+          if (TraceSuperWord && Verbose) {
+            tty->print_cr("SuperWord::mark_generations _ii_first error - found different generations in two nodes ");
+            ii->dump();
+            ii_err->dump();
+          }
+#endif
+          return -1; // this phi has Stores from different generations of unroll and cannot be simd/vectorized
+        }
+      }
+    }//for (DUIterator_Fast imax,
+  }//for (int i...
+
+  if (_ii_first == -1 || _ii_last == -1) {
+#ifndef PRODUCT
+    if (TraceSuperWord && Verbose) {
+      tty->print_cr("SuperWord::mark_generations unknown error, something vent wrong");
+    }
+#endif
+    return -1; // something vent wrong
+  }
+  // collect nodes in the first and last generations
+  assert(_iteration_first.length() == 0, "_iteration_first must be empty");
+  assert(_iteration_last.length() == 0, "_iteration_last must be empty");
+  for (int j = 0; j < _block.length(); j++) {
+    Node* n = _block.at(j);
+    node_idx_t gen = _clone_map.gen(n->_idx);
+    if ((signed)gen == _ii_first) {
+      _iteration_first.push(n);
+    } else if ((signed)gen == _ii_last) {
+      _iteration_last.push(n);
+    }
+  }
+
+  // building order of iterations
+  assert(_ii_order.length() == 0, "should be empty");
+  if (ii_err != 0) {
+    assert(in_bb(ii_err) && ii_err->is_Store(), "should be Store in bb");
+    Node* nd = ii_err;
+    while(_clone_map.gen(nd->_idx) != _ii_last) {
+      _ii_order.push(_clone_map.gen(nd->_idx));
+      bool found = false;
+      for (DUIterator_Fast imax, i = nd->fast_outs(imax); i < imax; i++) {
+        Node* use = nd->fast_out(i);
+        if (_clone_map.idx(use->_idx) == _clone_map.idx(nd->_idx) && use->as_Store()->in(MemNode::Memory) == nd) {
+          found = true;
+          nd = use;
+          break;
+        }
+      }//for
+
+      if (found == false) {
+#ifndef PRODUCT
+        if (TraceSuperWord && Verbose) {
+          tty->print_cr("SuperWord::mark_generations: Cannot build order of iterations - no dependent Store for %d", nd->_idx);
+        }
+#endif
+        _ii_order.clear();
+        return -1;
+      }
+    } //while
+    _ii_order.push(_clone_map.gen(nd->_idx));
+  }
+
+#ifndef PRODUCT
+  if (_vector_loop_debug) {
+    tty->print_cr("SuperWord::mark_generations");
+    tty->print_cr("First generation (%d) nodes:", _ii_first);
+    for (int ii = 0; ii < _iteration_first.length(); ii++)  _iteration_first.at(ii)->dump();
+    tty->print_cr("Last generation (%d) nodes:", _ii_last);
+    for (int ii = 0; ii < _iteration_last.length(); ii++)  _iteration_last.at(ii)->dump();
+    tty->print_cr(" ");
+
+    tty->print("SuperWord::List of generations: ");
+    for (int jj = 0; jj < _ii_order.length(); ++jj) {
+      tty->print("%d:%d ", jj, _ii_order.at(jj));
+    }
+    tty->print_cr(" ");
+  }
+#endif
+
+  return _ii_first;
+}
+
+bool SuperWord::fix_commutative_inputs(Node* gold, Node* fix) {
+  assert(gold->is_Add() && fix->is_Add() || gold->is_Mul() && fix->is_Mul(), "should be only Add or Mul nodes");
+  assert(_clone_map.idx(gold->_idx) == _clone_map.idx(fix->_idx), "should be clones of the same node");
+  Node* gin1 = gold->in(1);
+  Node* gin2 = gold->in(2);
+  Node* fin1 = fix->in(1);
+  Node* fin2 = fix->in(2);
+  bool swapped = false;
+
+  if (in_bb(gin1) && in_bb(gin2) && in_bb(fin1) && in_bb(fin1)) {
+    if (_clone_map.idx(gin1->_idx) == _clone_map.idx(fin1->_idx) &&
+        _clone_map.idx(gin2->_idx) == _clone_map.idx(fin2->_idx)) {
+      return true; // nothing to fix
+    }
+    if (_clone_map.idx(gin1->_idx) == _clone_map.idx(fin2->_idx) &&
+        _clone_map.idx(gin2->_idx) == _clone_map.idx(fin1->_idx)) {
+      fix->swap_edges(1, 2);
+      swapped = true;
+    }
+  }
+  // at least one input comes from outside of bb
+  if (gin1->_idx == fin1->_idx)  {
+    return true; // nothing to fix
+  }
+  if (!swapped && (gin1->_idx == fin2->_idx || gin2->_idx == fin1->_idx))  { //swapping is expensive, check condition first
+    fix->swap_edges(1, 2);
+    swapped = true;
+  }
+
+  if (swapped) {
+#ifndef PRODUCT
+    if (_vector_loop_debug) {
+      tty->print_cr("SuperWord::fix_commutative_inputs: fixed node %d", fix->_idx);
+    }
+#endif
+    return true;
+  }
+
+#ifndef PRODUCT
+  if (TraceSuperWord && Verbose) {
+    tty->print_cr("SuperWord::fix_commutative_inputs: cannot fix node %d", fix->_idx);
+  }
+#endif
+  return false;
+}
+
+bool SuperWord::pack_parallel() {
+#ifndef PRODUCT
+  if (_vector_loop_debug) {
+    tty->print_cr("SuperWord::pack_parallel: START");
+  }
+#endif
+
+  _packset.clear();
+
+  for (int ii = 0; ii < _iteration_first.length(); ii++) {
+    Node* nd = _iteration_first.at(ii);
+    if (in_bb(nd) && (nd->is_Load() || nd->is_Store() || nd->is_Add() || nd->is_Mul())) {
+      Node_List* pk = new Node_List();
+      pk->push(nd);
+      for (int gen = 1; gen < _ii_order.length(); ++gen) {
+        for (int kk = 0; kk < _block.length(); kk++) {
+          Node* clone = _block.at(kk);
+          if (_clone_map.idx(clone->_idx) == _clone_map.idx(nd->_idx) &&
+              _clone_map.gen(clone->_idx) == _ii_order.at(gen)) {
+            if (nd->is_Add() || nd->is_Mul()) {
+              fix_commutative_inputs(nd, clone);
+            }
+            pk->push(clone);
+            if (pk->size() == 4) {
+              _packset.append(pk);
+#ifndef PRODUCT
+              if (_vector_loop_debug) {
+                tty->print_cr("SuperWord::pack_parallel: added pack ");
+                pk->dump();
+              }
+#endif
+              if (_clone_map.gen(clone->_idx) != _ii_last) {
+                pk = new Node_List();
+              }
+            }
+            break;
+          }
+        }
+      }//for
+    }//if
+  }//for
+
+#ifndef PRODUCT
+  if (_vector_loop_debug) {
+    tty->print_cr("SuperWord::pack_parallel: END");
+  }
+#endif
+
+  return true;
+}
+
+bool SuperWord::hoist_loads_in_graph() {
+  GrowableArray<Node*> loads;
+
+#ifndef PRODUCT
+  if (_vector_loop_debug) {
+    tty->print_cr("SuperWord::hoist_loads_in_graph: total number _mem_slice_head.length() = %d", _mem_slice_head.length());
+  }
+#endif
+
+  for (int i = 0; i < _mem_slice_head.length(); i++) {
+    Node* n = _mem_slice_head.at(i);
+    if ( !in_bb(n) || !n->is_Phi() || n->bottom_type() != Type::MEMORY) {
+#ifndef PRODUCT
+      if (TraceSuperWord && Verbose) {
+        tty->print_cr("SuperWord::hoist_loads_in_graph: skipping unexpected node n=%d", n->_idx);
+      }
+#endif
+      continue;
+    }
+
+#ifndef PRODUCT
+    if (_vector_loop_debug) {
+      tty->print_cr("SuperWord::hoist_loads_in_graph: processing phi %d  = _mem_slice_head.at(%d);", n->_idx, i);
+    }
+#endif
+
+    for (DUIterator_Fast imax, i = n->fast_outs(imax); i < imax; i++) {
+      Node* ld = n->fast_out(i);
+      if (ld->is_Load() && ld->as_Load()->in(MemNode::Memory) == n && in_bb(ld)) {
+        for (int i = 0; i < _block.length(); i++) {
+          Node* ld2 = _block.at(i);
+          if (ld2->is_Load() &&
+              _clone_map.idx(ld->_idx) == _clone_map.idx(ld2->_idx) &&
+              _clone_map.gen(ld->_idx) != _clone_map.gen(ld2->_idx)) { // <= do not collect the first generation ld
+#ifndef PRODUCT
+            if (_vector_loop_debug) {
+              tty->print_cr("SuperWord::hoist_loads_in_graph: will try to hoist load ld2->_idx=%d, cloned from %d (ld->_idx=%d)",
+                            ld2->_idx, _clone_map.idx(ld->_idx), ld->_idx);
+            }
+#endif
+            // could not do on-the-fly, since iterator is immutable
+            loads.push(ld2);
+          }
+        }// for
+      }//if
+    }//for (DUIterator_Fast imax,
+  }//for (int i = 0; i
+
+  for (int i = 0; i < loads.length(); i++) {
+    LoadNode* ld = loads.at(i)->as_Load();
+    Node* phi = find_phi_for_mem_dep(ld);
+    if (phi != NULL) {
+#ifndef PRODUCT
+      if (_vector_loop_debug) {
+        tty->print_cr("SuperWord::hoist_loads_in_graph replacing MemNode::Memory(%d) edge in %d with one from %d",
+                      MemNode::Memory, ld->_idx, phi->_idx);
+      }
+#endif
+      _igvn.replace_input_of(ld, MemNode::Memory, phi);
+    }
+  }//for
+
+  restart(); // invalidate all basic structures, since we rebuilt the graph
+
+#ifndef PRODUCT
+  if (TraceSuperWord && Verbose) {
+    tty->print_cr("\nSuperWord::hoist_loads_in_graph() the graph was rebuilt, all structures invalidated and need rebuild");
+  }
+#endif
+  return true;
+}
+
--- a/hotspot/src/share/vm/opto/superword.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/superword.hpp	Wed Jul 05 20:35:10 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
@@ -40,7 +40,7 @@
 // Exploiting SuperWord Level Parallelism with
 //   Multimedia Instruction Sets
 // by
-//   Samuel Larsen and Saman Amarasighe
+//   Samuel Larsen and Saman Amarasinghe
 //   MIT Laboratory for Computer Science
 // date
 //   May 2000
@@ -218,8 +218,10 @@
   GrowableArray<Node*> _data_entry;      // Nodes with all inputs from outside
   GrowableArray<Node*> _mem_slice_head;  // Memory slice head nodes
   GrowableArray<Node*> _mem_slice_tail;  // Memory slice tail nodes
-
+  GrowableArray<Node*> _iteration_first; // nodes in the generation that has deps from phi
+  GrowableArray<Node*> _iteration_last;  // nodes in the generation that has deps to   phi
   GrowableArray<SWNodeInfo> _node_info;  // Info needed per node
+  CloneMap&                 _clone_map;  // map of nodes created in cloning
 
   MemNode* _align_to_ref;                // Memory reference that pre-loop will align to
 
@@ -250,6 +252,13 @@
   Node*          _bb;              // Current basic block
   PhiNode*       _iv;              // Induction var
   bool           _race_possible;   // In cases where SDMU is true
+  bool           _do_vector_loop;  // whether to do vectorization/simd style
+  bool           _vector_loop_debug; // provide more printing in debug mode
+  int            _num_work_vecs;   // Number of non memory vector operations
+  int            _num_reductions;  // Number of reduction expressions applied
+  int            _ii_first;        // generation with direct deps from mem phi
+  int            _ii_last;         // generation with direct deps to   mem phi
+  GrowableArray<int> _ii_order;
 
   // Accessors
   Arena* arena()                   { return _arena; }
@@ -324,6 +333,22 @@
   int get_iv_adjustment(MemNode* mem);
   // Can the preloop align the reference to position zero in the vector?
   bool ref_is_alignable(SWPointer& p);
+  // rebuild the graph so all loads in different iterations of cloned loop become dependant on phi node (in _do_vector_loop only)
+  bool hoist_loads_in_graph();
+  // Test whether MemNode::Memory dependency to the same load but in the first iteration of this loop is coming from memory phi
+  // Return false if failed.
+  Node* find_phi_for_mem_dep(LoadNode* ld);
+  // Return same node but from the first generation. Return 0, if not found
+  Node* first_node(Node* nd);
+  // Return same node as this but from the last generation. Return 0, if not found
+  Node* last_node(Node* n);
+  // Mark nodes belonging to first and last generation,
+  // returns first generation index or -1 if vectorization/simd is impossible
+  int mark_generations();
+  // swapping inputs of commutative instruction (Add or Mul)
+  bool fix_commutative_inputs(Node* gold, Node* fix);
+  // make packs forcefully (in _do_vector_loop only)
+  bool pack_parallel();
   // Construct dependency graph.
   void dependence_graph();
   // Return a memory slice (node list) in predecessor order starting at "start"
@@ -417,6 +442,8 @@
   // Is the use of d1 in u1 at the same operand position as d2 in u2?
   bool opnd_positions_match(Node* d1, Node* u1, Node* d2, Node* u2);
   void init();
+  // clean up some basic structures - used if the ideal graph was rebuilt
+  void restart();
 
   // print methods
   void print_packset();
@@ -439,7 +466,7 @@
 
   Node* _base;         // NULL if unsafe nonheap reference
   Node* _adr;          // address pointer
-  jint  _scale;        // multipler for iv (in bytes), 0 if no loop iv
+  jint  _scale;        // multiplier for iv (in bytes), 0 if no loop iv
   jint  _offset;       // constant offset (in bytes)
   Node* _invar;        // invariant offset (in bytes), NULL if none
   bool  _negate_invar; // if true then use: (0 - _invar)
--- a/hotspot/src/share/vm/opto/type.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/type.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -68,16 +68,19 @@
   { Bad,             T_ILLEGAL,    "vectord:",      false, Op_RegD,              relocInfo::none          },  // VectorD
   { Bad,             T_ILLEGAL,    "vectorx:",      false, 0,                    relocInfo::none          },  // VectorX
   { Bad,             T_ILLEGAL,    "vectory:",      false, 0,                    relocInfo::none          },  // VectorY
+  { Bad,             T_ILLEGAL,    "vectorz:",      false, 0,                    relocInfo::none          },  // VectorZ
 #elif defined(PPC64)
   { Bad,             T_ILLEGAL,    "vectors:",      false, 0,                    relocInfo::none          },  // VectorS
   { Bad,             T_ILLEGAL,    "vectord:",      false, Op_RegL,              relocInfo::none          },  // VectorD
   { Bad,             T_ILLEGAL,    "vectorx:",      false, 0,                    relocInfo::none          },  // VectorX
   { Bad,             T_ILLEGAL,    "vectory:",      false, 0,                    relocInfo::none          },  // VectorY
+  { Bad,             T_ILLEGAL,    "vectorz:",      false, 0,                    relocInfo::none          },  // VectorZ
 #else // all other
   { Bad,             T_ILLEGAL,    "vectors:",      false, Op_VecS,              relocInfo::none          },  // VectorS
   { Bad,             T_ILLEGAL,    "vectord:",      false, Op_VecD,              relocInfo::none          },  // VectorD
   { Bad,             T_ILLEGAL,    "vectorx:",      false, Op_VecX,              relocInfo::none          },  // VectorX
   { Bad,             T_ILLEGAL,    "vectory:",      false, Op_VecY,              relocInfo::none          },  // VectorY
+  { Bad,             T_ILLEGAL,    "vectorz:",      false, Op_VecZ,              relocInfo::none          },  // VectorZ
 #endif
   { Bad,             T_ADDRESS,    "anyptr:",       false, Op_RegP,              relocInfo::none          },  // AnyPtr
   { Bad,             T_ADDRESS,    "rawptr:",       false, Op_RegP,              relocInfo::none          },  // RawPtr
@@ -503,10 +506,14 @@
   if (Matcher::vector_size_supported(T_FLOAT,8)) {
     TypeVect::VECTY = TypeVect::make(T_FLOAT,8);
   }
+  if (Matcher::vector_size_supported(T_FLOAT,16)) {
+    TypeVect::VECTZ = TypeVect::make(T_FLOAT,16);
+  }
   mreg2type[Op_VecS] = TypeVect::VECTS;
   mreg2type[Op_VecD] = TypeVect::VECTD;
   mreg2type[Op_VecX] = TypeVect::VECTX;
   mreg2type[Op_VecY] = TypeVect::VECTY;
+  mreg2type[Op_VecZ] = TypeVect::VECTZ;
 
   // Restore working type arena.
   current->set_type_arena(save);
@@ -798,6 +805,7 @@
   Bad,          // VectorD - handled in v-call
   Bad,          // VectorX - handled in v-call
   Bad,          // VectorY - handled in v-call
+  Bad,          // VectorZ - handled in v-call
 
   Bad,          // AnyPtr - handled in v-call
   Bad,          // RawPtr - handled in v-call
@@ -2051,6 +2059,7 @@
 const TypeVect *TypeVect::VECTD = NULL; //  64-bit vectors
 const TypeVect *TypeVect::VECTX = NULL; // 128-bit vectors
 const TypeVect *TypeVect::VECTY = NULL; // 256-bit vectors
+const TypeVect *TypeVect::VECTZ = NULL; // 512-bit vectors
 
 //------------------------------make-------------------------------------------
 const TypeVect* TypeVect::make(const Type *elem, uint length) {
@@ -2070,6 +2079,8 @@
     return (TypeVect*)(new TypeVectX(elem, length))->hashcons();
   case Op_VecY:
     return (TypeVect*)(new TypeVectY(elem, length))->hashcons();
+  case Op_VecZ:
+    return (TypeVect*)(new TypeVectZ(elem, length))->hashcons();
   }
  ShouldNotReachHere();
   return NULL;
@@ -2093,7 +2104,8 @@
   case VectorS:
   case VectorD:
   case VectorX:
-  case VectorY: {                // Meeting 2 vectors?
+  case VectorY:
+  case VectorZ: {                // Meeting 2 vectors?
     const TypeVect* v = t->is_vect();
     assert(  base() == v->base(), "");
     assert(length() == v->length(), "");
@@ -2151,6 +2163,8 @@
     st->print("vectorx["); break;
   case VectorY:
     st->print("vectory["); break;
+  case VectorZ:
+    st->print("vectorz["); break;
   default:
     ShouldNotReachHere();
   }
--- a/hotspot/src/share/vm/opto/type.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/type.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -57,6 +57,7 @@
 class     TypeVectD;
 class     TypeVectX;
 class     TypeVectY;
+class     TypeVectZ;
 class   TypePtr;
 class     TypeRawPtr;
 class     TypeOopPtr;
@@ -90,6 +91,7 @@
     VectorD,                    //  64bit Vector types
     VectorX,                    // 128bit Vector types
     VectorY,                    // 256bit Vector types
+    VectorZ,                    // 512bit Vector types
 
     AnyPtr,                     // Any old raw, klass, inst, or array pointer
     RawPtr,                     // Raw (non-oop) pointers
@@ -729,6 +731,7 @@
   static const TypeVect *VECTD;
   static const TypeVect *VECTX;
   static const TypeVect *VECTY;
+  static const TypeVect *VECTZ;
 
 #ifndef PRODUCT
   virtual void dump2(Dict &d, uint, outputStream *st) const; // Specialized per-Type dumping
@@ -755,6 +758,11 @@
   TypeVectY(const Type* elem, uint length) : TypeVect(VectorY, elem, length) {}
 };
 
+class TypeVectZ : public TypeVect {
+  friend class TypeVect;
+  TypeVectZ(const Type* elem, uint length) : TypeVect(VectorZ, elem, length) {}
+};
+
 //------------------------------TypePtr----------------------------------------
 // Class of machine Pointer Types: raw data, instances or arrays.
 // If the _base enum is AnyPtr, then this refers to all of the above.
@@ -1568,12 +1576,12 @@
 }
 
 inline const TypeVect *Type::is_vect() const {
-  assert( _base >= VectorS && _base <= VectorY, "Not a Vector" );
+  assert( _base >= VectorS && _base <= VectorZ, "Not a Vector" );
   return (TypeVect*)this;
 }
 
 inline const TypeVect *Type::isa_vect() const {
-  return (_base >= VectorS && _base <= VectorY) ? (TypeVect*)this : NULL;
+  return (_base >= VectorS && _base <= VectorZ) ? (TypeVect*)this : NULL;
 }
 
 inline const TypePtr *Type::is_ptr() const {
--- a/hotspot/src/share/vm/opto/vectornode.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/vectornode.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -77,6 +77,9 @@
     case T_INT:    return Op_MulVI;
     }
     ShouldNotReachHere();
+  case Op_MulL:
+    assert(bt == T_LONG, "must be");
+    return Op_MulVL;
   case Op_MulF:
     assert(bt == T_FLOAT, "must be");
     return Op_MulVF;
@@ -267,6 +270,7 @@
 
   case Op_MulVS: return new MulVSNode(n1, n2, vt);
   case Op_MulVI: return new MulVINode(n1, n2, vt);
+  case Op_MulVL: return new MulVLNode(n1, n2, vt);
   case Op_MulVF: return new MulVFNode(n1, n2, vt);
   case Op_MulVD: return new MulVDNode(n1, n2, vt);
 
@@ -463,6 +467,10 @@
       assert(bt == T_INT, "must be");
       vopc = Op_MulReductionVI;
       break;
+    case Op_MulL:
+      assert(bt == T_LONG, "must be");
+      vopc = Op_MulReductionVL;
+      break;
     case Op_MulF:
       assert(bt == T_FLOAT, "must be");
       vopc = Op_MulReductionVF;
@@ -492,6 +500,7 @@
   case Op_AddReductionVF: return new AddReductionVFNode(ctrl, n1, n2);
   case Op_AddReductionVD: return new AddReductionVDNode(ctrl, n1, n2);
   case Op_MulReductionVI: return new MulReductionVINode(ctrl, n1, n2);
+  case Op_MulReductionVL: return new MulReductionVLNode(ctrl, n1, n2);
   case Op_MulReductionVF: return new MulReductionVFNode(ctrl, n1, n2);
   case Op_MulReductionVD: return new MulReductionVDNode(ctrl, n1, n2);
   }
--- a/hotspot/src/share/vm/opto/vectornode.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/opto/vectornode.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -90,6 +90,30 @@
   virtual int Opcode() const;
 };
 
+//------------------------------AddVLNode--------------------------------------
+// Vector add long
+class AddVLNode : public VectorNode {
+public:
+  AddVLNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1, in2, vt) {}
+  virtual int Opcode() const;
+};
+
+//------------------------------AddVFNode--------------------------------------
+// Vector add float
+class AddVFNode : public VectorNode {
+public:
+  AddVFNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1, in2, vt) {}
+  virtual int Opcode() const;
+};
+
+//------------------------------AddVDNode--------------------------------------
+// Vector add double
+class AddVDNode : public VectorNode {
+public:
+  AddVDNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1, in2, vt) {}
+  virtual int Opcode() const;
+};
+
 //------------------------------ReductionNode------------------------------------
 // Perform reduction of a vector
 class ReductionNode : public Node {
@@ -121,22 +145,6 @@
   virtual uint ideal_reg() const { return Op_RegL; }
 };
 
-//------------------------------AddVLNode--------------------------------------
-// Vector add long
-class AddVLNode : public VectorNode {
- public:
-  AddVLNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
-  virtual int Opcode() const;
-};
-
-//------------------------------AddVFNode--------------------------------------
-// Vector add float
-class AddVFNode : public VectorNode {
- public:
-  AddVFNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
-  virtual int Opcode() const;
-};
-
 //------------------------------AddReductionVFNode--------------------------------------
 // Vector add float as a reduction
 class AddReductionVFNode : public ReductionNode {
@@ -147,14 +155,6 @@
   virtual uint ideal_reg() const { return Op_RegF; }
 };
 
-//------------------------------AddVDNode--------------------------------------
-// Vector add double
-class AddVDNode : public VectorNode {
- public:
-  AddVDNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
-  virtual int Opcode() const;
-};
-
 //------------------------------AddReductionVDNode--------------------------------------
 // Vector add double as a reduction
 class AddReductionVDNode : public ReductionNode {
@@ -229,6 +229,30 @@
   virtual int Opcode() const;
 };
 
+//------------------------------MulVLNode--------------------------------------
+// Vector multiply long
+class MulVLNode : public VectorNode {
+public:
+  MulVLNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1, in2, vt) {}
+  virtual int Opcode() const;
+};
+
+//------------------------------MulVFNode--------------------------------------
+// Vector multiply float
+class MulVFNode : public VectorNode {
+public:
+  MulVFNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1, in2, vt) {}
+  virtual int Opcode() const;
+};
+
+//------------------------------MulVDNode--------------------------------------
+// Vector multiply double
+class MulVDNode : public VectorNode {
+public:
+  MulVDNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1, in2, vt) {}
+  virtual int Opcode() const;
+};
+
 //------------------------------MulReductionVINode--------------------------------------
 // Vector multiply int as a reduction
 class MulReductionVINode : public ReductionNode {
@@ -239,12 +263,14 @@
   virtual uint ideal_reg() const { return Op_RegI; }
 };
 
-//------------------------------MulVFNode--------------------------------------
-// Vector multiply float
-class MulVFNode : public VectorNode {
- public:
-  MulVFNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
+//------------------------------MulReductionVLNode--------------------------------------
+// Vector multiply int as a reduction
+class MulReductionVLNode : public ReductionNode {
+public:
+  MulReductionVLNode(Node *ctrl, Node* in1, Node* in2) : ReductionNode(ctrl, in1, in2) {}
   virtual int Opcode() const;
+  virtual const Type* bottom_type() const { return TypeLong::LONG; }
+  virtual uint ideal_reg() const { return Op_RegI; }
 };
 
 //------------------------------MulReductionVFNode--------------------------------------
@@ -257,14 +283,6 @@
   virtual uint ideal_reg() const { return Op_RegF; }
 };
 
-//------------------------------MulVDNode--------------------------------------
-// Vector multiply double
-class MulVDNode : public VectorNode {
- public:
-  MulVDNode(Node* in1, Node* in2, const TypeVect* vt) : VectorNode(in1,in2,vt) {}
-  virtual int Opcode() const;
-};
-
 //------------------------------MulReductionVDNode--------------------------------------
 // Vector multiply double as a reduction
 class MulReductionVDNode : public ReductionNode {
--- a/hotspot/src/share/vm/prims/methodHandles.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/prims/methodHandles.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -186,7 +186,9 @@
 oop MethodHandles::init_method_MemberName(Handle mname, CallInfo& info) {
   assert(info.resolved_appendix().is_null(), "only normal methods here");
   methodHandle m = info.resolved_method();
+  assert(m.not_null(), "null method handle");
   KlassHandle m_klass = m->method_holder();
+  assert(m.not_null(), "null holder for method handle");
   int flags = (jushort)( m->access_flags().as_short() & JVM_RECOGNIZED_METHOD_MODIFIERS );
   int vmindex = Method::invalid_vtable_index;
 
--- a/hotspot/src/share/vm/runtime/frame.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/runtime/frame.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -30,11 +30,9 @@
 #include "runtime/monitorChunk.hpp"
 #include "runtime/registerMap.hpp"
 #include "utilities/top.hpp"
-#ifdef ZERO
 #ifdef TARGET_ARCH_zero
 # include "stack_zero.hpp"
 #endif
-#endif
 
 typedef class BytecodeInterpreter* interpreterState;
 
--- a/hotspot/src/share/vm/runtime/frame.inline.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/runtime/frame.inline.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -31,14 +31,12 @@
 #include "oops/method.hpp"
 #include "runtime/frame.hpp"
 #include "runtime/signature.hpp"
-#ifdef ZERO
 #ifdef TARGET_ARCH_zero
 # include "entryFrame_zero.hpp"
 # include "fakeStubFrame_zero.hpp"
 # include "interpreterFrame_zero.hpp"
 # include "sharkFrame_zero.hpp"
 #endif
-#endif
 
 inline bool frame::is_entry_frame() const {
   return StubRoutines::returns_to_call_stub(pc());
--- a/hotspot/src/share/vm/runtime/interfaceSupport.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/runtime/interfaceSupport.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -239,7 +239,7 @@
     CodeBlob* cb = sfs.current()->cb();
     if (cb != NULL && cb->oop_maps() ) {
       // Find oopmap for current method
-      OopMap* map = cb->oop_map_for_return_address(sfs.current()->pc());
+      const ImmutableOopMap* map = cb->oop_map_for_return_address(sfs.current()->pc());
       assert(map != NULL, "no oopmap found for pc");
       found = map->has_derived_pointer();
     }
--- a/hotspot/src/share/vm/runtime/java.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/runtime/java.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -651,11 +651,15 @@
       minor = micro;
       micro = 0;
     }
+    // Incompatible with pre-4243978 JDK.
+    if (info.pending_list_uses_discovered_field == 0) {
+      vm_exit_during_initialization(
+        "Incompatible JDK is not using Reference.discovered field for pending list");
+    }
     _current = JDK_Version(major, minor, micro, info.update_version,
                            info.special_update_version, build,
                            info.thread_park_blocker == 1,
-                           info.post_vm_init_hook_enabled == 1,
-                           info.pending_list_uses_discovered_field == 1);
+                           info.post_vm_init_hook_enabled == 1);
   }
 }
 
--- a/hotspot/src/share/vm/runtime/java.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/runtime/java.hpp	Wed Jul 05 20:35:10 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
@@ -91,7 +91,6 @@
   bool _partially_initialized;
 
   bool _thread_park_blocker;
-  bool _pending_list_uses_discovered_field;
   bool _post_vm_init_hook_enabled;
 
   bool is_valid() const {
@@ -114,18 +113,17 @@
 
   JDK_Version() : _major(0), _minor(0), _micro(0), _update(0),
                   _special(0), _build(0), _partially_initialized(false),
-                  _thread_park_blocker(false), _post_vm_init_hook_enabled(false),
-                  _pending_list_uses_discovered_field(false) {}
+                  _thread_park_blocker(false), _post_vm_init_hook_enabled(false)
+                  {}
 
   JDK_Version(uint8_t major, uint8_t minor = 0, uint8_t micro = 0,
               uint8_t update = 0, uint8_t special = 0, uint8_t build = 0,
-              bool thread_park_blocker = false, bool post_vm_init_hook_enabled = false,
-              bool pending_list_uses_discovered_field = false) :
+              bool thread_park_blocker = false, bool post_vm_init_hook_enabled = false) :
       _major(major), _minor(minor), _micro(micro), _update(update),
       _special(special), _build(build), _partially_initialized(false),
       _thread_park_blocker(thread_park_blocker),
-      _post_vm_init_hook_enabled(post_vm_init_hook_enabled),
-      _pending_list_uses_discovered_field(pending_list_uses_discovered_field) {}
+      _post_vm_init_hook_enabled(post_vm_init_hook_enabled)
+      {}
 
   // Returns the current running JDK version
   static JDK_Version current() { return _current; }
@@ -152,10 +150,6 @@
   bool post_vm_init_hook_enabled() const {
     return _post_vm_init_hook_enabled;
   }
-  // For compatibility wrt pre-4965777 JDK's
-  bool pending_list_uses_discovered_field() const {
-    return _pending_list_uses_discovered_field;
-  }
 
   // Performs a full ordering comparison using all fields (update, build, etc.)
   int compare(const JDK_Version& other) const;
--- a/hotspot/src/share/vm/runtime/task.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/runtime/task.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -53,7 +53,7 @@
   if (ProfilerCheckIntervals) {
     _ticks++;
     _timer.stop();
-    int ms = (int)(_timer.seconds() * 1000.0);
+    int ms = (int)_timer.milliseconds();
     _timer.reset();
     _timer.start();
     if (ms >= PeriodicTask::max_interval) ms = PeriodicTask::max_interval - 1;
--- a/hotspot/src/share/vm/runtime/thread.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/runtime/thread.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -190,6 +190,7 @@
   set_stack_size(0);
   set_self_raw_id(0);
   set_lgrp_id(-1);
+  DEBUG_ONLY(clear_suspendible_thread();)
 
   // allocated data structures
   set_osthread(NULL);
@@ -3230,6 +3231,8 @@
 
   // Initialize java_lang.System (needed before creating the thread)
   initialize_class(vmSymbols::java_lang_System(), CHECK);
+  // The VM creates & returns objects of this class. Make sure it's initialized.
+  initialize_class(vmSymbols::java_lang_Class(), CHECK);
   initialize_class(vmSymbols::java_lang_ThreadGroup(), CHECK);
   Handle thread_group = create_initial_thread_group(CHECK);
   Universe::set_main_thread_group(thread_group());
@@ -3241,9 +3244,6 @@
   java_lang_Thread::set_thread_status(thread_object,
                                       java_lang_Thread::RUNNABLE);
 
-  // The VM creates & returns objects of this class. Make sure it's initialized.
-  initialize_class(vmSymbols::java_lang_Class(), CHECK);
-
   // The VM preresolves methods to these classes. Make sure that they get initialized
   initialize_class(vmSymbols::java_lang_reflect_Method(), CHECK);
   initialize_class(vmSymbols::java_lang_ref_Finalizer(), CHECK);
@@ -4210,13 +4210,13 @@
                Abstract_VM_Version::vm_info_string());
   st->cr();
 
-#if INCLUDE_ALL_GCS
+#if INCLUDE_SERVICES
   // Dump concurrent locks
   ConcurrentLocksDump concurrent_locks;
   if (print_concurrent_locks) {
     concurrent_locks.dump_at_safepoint();
   }
-#endif // INCLUDE_ALL_GCS
+#endif // INCLUDE_SERVICES
 
   ALL_JAVA_THREADS(p) {
     ResourceMark rm;
@@ -4229,11 +4229,11 @@
       }
     }
     st->cr();
-#if INCLUDE_ALL_GCS
+#if INCLUDE_SERVICES
     if (print_concurrent_locks) {
       concurrent_locks.print_locks_on(p, st);
     }
-#endif // INCLUDE_ALL_GCS
+#endif // INCLUDE_SERVICES
   }
 
   VMThread::vm_thread()->print_on(st);
--- a/hotspot/src/share/vm/runtime/thread.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/runtime/thread.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -51,11 +51,9 @@
 #include "gc_implementation/g1/dirtyCardQueue.hpp"
 #include "gc_implementation/g1/satbQueue.hpp"
 #endif // INCLUDE_ALL_GCS
-#ifdef ZERO
 #ifdef TARGET_ARCH_zero
 # include "stack_zero.hpp"
 #endif
-#endif
 
 class ThreadSafepointState;
 class ThreadProfiler;
@@ -206,11 +204,25 @@
  private:
   int _num_nested_signal;
 
+  DEBUG_ONLY(bool _suspendible_thread;)
+
  public:
   void enter_signal_handler() { _num_nested_signal++; }
   void leave_signal_handler() { _num_nested_signal--; }
   bool is_inside_signal_handler() const { return _num_nested_signal > 0; }
 
+#ifdef ASSERT
+  void set_suspendible_thread() {
+    _suspendible_thread = true;
+  }
+
+  void clear_suspendible_thread() {
+    _suspendible_thread = false;
+  }
+
+  bool is_suspendible_thread() { return _suspendible_thread; }
+#endif
+
  private:
   // Active_handles points to a block of handles
   JNIHandleBlock* _active_handles;
--- a/hotspot/src/share/vm/runtime/timer.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/runtime/timer.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -28,9 +28,12 @@
 #include "utilities/ostream.hpp"
 
 double TimeHelper::counter_to_seconds(jlong counter) {
-  double count = (double) counter;
   double freq  = (double) os::elapsed_frequency();
-  return counter/freq;
+  return counter / freq;
+}
+
+double TimeHelper::counter_to_millis(jlong counter) {
+  return counter_to_seconds(counter) * 1000.0;
 }
 
 void elapsedTimer::add(elapsedTimer t) {
@@ -56,8 +59,7 @@
 }
 
 jlong elapsedTimer::milliseconds() const {
-  jlong ticks_per_ms = os::elapsed_frequency() / 1000;
-  return _counter / ticks_per_ms;
+  return TimeHelper::counter_to_millis(_counter);
 }
 
 jlong elapsedTimer::active_ticks() const {
@@ -86,11 +88,8 @@
 
 jlong TimeStamp::milliseconds() const {
   assert(is_updated(), "must not be clear");
-
   jlong new_count = os::elapsed_counter();
-  jlong count = new_count - _counter;
-  jlong ticks_per_ms = os::elapsed_frequency() / 1000;
-  return count / ticks_per_ms;
+  return TimeHelper::counter_to_millis(new_count - _counter);
 }
 
 jlong TimeStamp::ticks_since_update() const {
--- a/hotspot/src/share/vm/runtime/timer.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/runtime/timer.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -123,6 +123,7 @@
 class TimeHelper {
  public:
   static double counter_to_seconds(jlong counter);
+  static double counter_to_millis(jlong counter);
 };
 
 #endif // SHARE_VM_RUNTIME_TIMER_HPP
--- a/hotspot/src/share/vm/runtime/vmStructs.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/runtime/vmStructs.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -860,7 +860,7 @@
   nonstatic_field(CodeBlob,                    _frame_complete_offset,                        int)                                   \
   nonstatic_field(CodeBlob,                    _data_offset,                                  int)                                   \
   nonstatic_field(CodeBlob,                    _frame_size,                                   int)                                   \
-  nonstatic_field(CodeBlob,                    _oop_maps,                                     OopMapSet*)                            \
+  nonstatic_field(CodeBlob,                    _oop_maps,                                     ImmutableOopMapSet*)                   \
                                                                                                                                      \
   nonstatic_field(RuntimeStub,                 _caller_must_gc_arguments,                     bool)                                  \
                                                                                                                                      \
@@ -966,13 +966,19 @@
                                                                                                                                      \
   nonstatic_field(OopMap,                      _pc_offset,                                    int)                                   \
   nonstatic_field(OopMap,                      _omv_count,                                    int)                                   \
-  nonstatic_field(OopMap,                      _omv_data_size,                                int)                                   \
-  nonstatic_field(OopMap,                      _omv_data,                                     unsigned char*)                        \
   nonstatic_field(OopMap,                      _write_stream,                                 CompressedWriteStream*)                \
   nonstatic_field(OopMapSet,                   _om_count,                                     int)                                   \
   nonstatic_field(OopMapSet,                   _om_size,                                      int)                                   \
   nonstatic_field(OopMapSet,                   _om_data,                                      OopMap**)                              \
                                                                                                                                      \
+  nonstatic_field(ImmutableOopMapSet,          _count,                                        int)                                   \
+  nonstatic_field(ImmutableOopMapSet,          _size,                                         int)                                   \
+                                                                                                                                     \
+  nonstatic_field(ImmutableOopMapPair,         _pc_offset,                                    int)                                   \
+  nonstatic_field(ImmutableOopMapPair,         _oopmap_offset,                                int)                                   \
+                                                                                                                                     \
+  nonstatic_field(ImmutableOopMap,             _count,                                        int)                                   \
+                                                                                                                                     \
   /*********************************/                                                                                                \
   /* JNIHandles and JNIHandleBlock */                                                                                                \
   /*********************************/                                                                                                \
@@ -1689,6 +1695,9 @@
                                                                           \
   declare_toplevel_type(OopMap)                                           \
   declare_toplevel_type(OopMapSet)                                        \
+  declare_toplevel_type(ImmutableOopMapSet)                               \
+  declare_toplevel_type(ImmutableOopMapPair)                              \
+  declare_toplevel_type(ImmutableOopMap)                                  \
                                                                           \
   /********************/                                                  \
   /* CompressedStream */                                                  \
@@ -2001,6 +2010,8 @@
   declare_c2_type(SubVFNode, VectorNode)                                  \
   declare_c2_type(SubVDNode, VectorNode)                                  \
   declare_c2_type(MulVSNode, VectorNode)                                  \
+  declare_c2_type(MulVLNode, VectorNode)                                  \
+  declare_c2_type(MulReductionVLNode, ReductionNode)                      \
   declare_c2_type(MulVINode, VectorNode)                                  \
   declare_c2_type(MulReductionVINode, ReductionNode)                      \
   declare_c2_type(MulVFNode, VectorNode)                                  \
--- a/hotspot/src/share/vm/runtime/vm_version.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/runtime/vm_version.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -78,7 +78,7 @@
 int Abstract_VM_Version::_vm_micro_version = 0;
 int Abstract_VM_Version::_vm_build_number = 0;
 bool Abstract_VM_Version::_initialized = false;
-int Abstract_VM_Version::_parallel_worker_threads = 0;
+unsigned int Abstract_VM_Version::_parallel_worker_threads = 0;
 bool Abstract_VM_Version::_parallel_worker_threads_initialized = false;
 
 #ifdef ASSERT
--- a/hotspot/src/share/vm/runtime/vm_version.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/runtime/vm_version.hpp	Wed Jul 05 20:35:10 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
@@ -48,7 +48,7 @@
   static int          _vm_micro_version;
   static int          _vm_build_number;
   static bool         _initialized;
-  static int          _parallel_worker_threads;
+  static unsigned int _parallel_worker_threads;
   static bool         _parallel_worker_threads_initialized;
   static int          _reserve_for_allocation_prefetch;
 
--- a/hotspot/src/share/vm/utilities/hashtable.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/utilities/hashtable.cpp	Wed Jul 05 20:35:10 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
@@ -381,3 +381,4 @@
 template class BasicHashtable<mtSymbol>;
 template class BasicHashtable<mtCode>;
 template class BasicHashtable<mtInternal>;
+template class BasicHashtable<mtCompiler>;
--- a/hotspot/src/share/vm/utilities/taskqueue.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/utilities/taskqueue.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2001, 2014, 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
@@ -31,8 +31,6 @@
 #include "utilities/stack.inline.hpp"
 #include "utilities/taskqueue.hpp"
 
-PRAGMA_FORMAT_MUTE_WARNINGS_FOR_GCC
-
 #ifdef TRACESPINNING
 uint ParallelTaskTerminator::_total_yields = 0;
 uint ParallelTaskTerminator::_total_spins = 0;
@@ -131,7 +129,7 @@
 }
 
 ParallelTaskTerminator::
-ParallelTaskTerminator(int n_threads, TaskQueueSetSuper* queue_set) :
+ParallelTaskTerminator(uint n_threads, TaskQueueSetSuper* queue_set) :
   _n_threads(n_threads),
   _queue_set(queue_set),
   _offered_termination(0) {}
@@ -154,7 +152,7 @@
 ParallelTaskTerminator::offer_termination(TerminatorTerminator* terminator) {
   assert(_n_threads > 0, "Initialization is incorrect");
   assert(_offered_termination < _n_threads, "Invariant");
-  Atomic::inc(&_offered_termination);
+  Atomic::inc((int *)&_offered_termination);
 
   uint yield_count = 0;
   // Number of hard spin loops done since last yield
@@ -216,8 +214,8 @@
       } else {
         if (PrintGCDetails && Verbose) {
          gclog_or_tty->print_cr("ParallelTaskTerminator::offer_termination() "
-           "thread %d sleeps after %d yields",
-           Thread::current(), yield_count);
+           "thread " PTR_FORMAT " sleeps after %u yields",
+           p2i(Thread::current()), yield_count);
         }
         yield_count = 0;
         // A sleep will cause this processor to seek work on another processor's
@@ -232,7 +230,7 @@
 #endif
       if (peek_in_queue_set() ||
           (terminator != NULL && terminator->should_exit_termination())) {
-        Atomic::dec(&_offered_termination);
+        Atomic::dec((int *)&_offered_termination);
         assert(_offered_termination < _n_threads, "Invariant");
         return false;
       }
@@ -265,7 +263,7 @@
 }
 #endif // ASSERT
 
-void ParallelTaskTerminator::reset_for_reuse(int n_threads) {
+void ParallelTaskTerminator::reset_for_reuse(uint n_threads) {
   reset_for_reuse();
   _n_threads = n_threads;
 }
--- a/hotspot/src/share/vm/utilities/taskqueue.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/utilities/taskqueue.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2001, 2014, 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
@@ -26,9 +26,6 @@
 #define SHARE_VM_UTILITIES_TASKQUEUE_HPP
 
 #include "memory/allocation.hpp"
-#include "memory/allocation.inline.hpp"
-#include "runtime/mutex.hpp"
-#include "runtime/orderAccess.inline.hpp"
 #include "utilities/stack.hpp"
 
 // Simple TaskQueue stats that are collected by default in debug builds.
@@ -134,11 +131,7 @@
       if (_fields._top == 0) ++_fields._tag;
     }
 
-    Age cmpxchg(const Age new_age, const Age old_age) volatile {
-      return (size_t) Atomic::cmpxchg_ptr((intptr_t)new_age._data,
-                                          (volatile intptr_t *)&_data,
-                                          (intptr_t)old_age._data);
-    }
+    Age cmpxchg(const Age new_age, const Age old_age) volatile;
 
     bool operator ==(const Age& other) const { return _data == other._data; }
 
@@ -315,121 +308,6 @@
   assert(sizeof(Age) == sizeof(size_t), "Depends on this.");
 }
 
-template<class E, MEMFLAGS F, unsigned int N>
-void GenericTaskQueue<E, F, N>::initialize() {
-  _elems = _array_allocator.allocate(N);
-}
-
-template<class E, MEMFLAGS F, unsigned int N>
-void GenericTaskQueue<E, F, N>::oops_do(OopClosure* f) {
-  // tty->print_cr("START OopTaskQueue::oops_do");
-  uint iters = size();
-  uint index = _bottom;
-  for (uint i = 0; i < iters; ++i) {
-    index = decrement_index(index);
-    // tty->print_cr("  doing entry %d," INTPTR_T " -> " INTPTR_T,
-    //            index, &_elems[index], _elems[index]);
-    E* t = (E*)&_elems[index];      // cast away volatility
-    oop* p = (oop*)t;
-    assert((*t)->is_oop_or_null(), err_msg("Expected an oop or NULL at " PTR_FORMAT, p2i(*t)));
-    f->do_oop(p);
-  }
-  // tty->print_cr("END OopTaskQueue::oops_do");
-}
-
-template<class E, MEMFLAGS F, unsigned int N>
-bool GenericTaskQueue<E, F, N>::push_slow(E t, uint dirty_n_elems) {
-  if (dirty_n_elems == N - 1) {
-    // Actually means 0, so do the push.
-    uint localBot = _bottom;
-    // g++ complains if the volatile result of the assignment is
-    // unused, so we cast the volatile away.  We cannot cast directly
-    // to void, because gcc treats that as not using the result of the
-    // assignment.  However, casting to E& means that we trigger an
-    // unused-value warning.  So, we cast the E& to void.
-    (void)const_cast<E&>(_elems[localBot] = t);
-    OrderAccess::release_store(&_bottom, increment_index(localBot));
-    TASKQUEUE_STATS_ONLY(stats.record_push());
-    return true;
-  }
-  return false;
-}
-
-// pop_local_slow() is done by the owning thread and is trying to
-// get the last task in the queue.  It will compete with pop_global()
-// that will be used by other threads.  The tag age is incremented
-// whenever the queue goes empty which it will do here if this thread
-// gets the last task or in pop_global() if the queue wraps (top == 0
-// and pop_global() succeeds, see pop_global()).
-template<class E, MEMFLAGS F, unsigned int N>
-bool GenericTaskQueue<E, F, N>::pop_local_slow(uint localBot, Age oldAge) {
-  // This queue was observed to contain exactly one element; either this
-  // thread will claim it, or a competing "pop_global".  In either case,
-  // the queue will be logically empty afterwards.  Create a new Age value
-  // that represents the empty queue for the given value of "_bottom".  (We
-  // must also increment "tag" because of the case where "bottom == 1",
-  // "top == 0".  A pop_global could read the queue element in that case,
-  // then have the owner thread do a pop followed by another push.  Without
-  // the incrementing of "tag", the pop_global's CAS could succeed,
-  // allowing it to believe it has claimed the stale element.)
-  Age newAge((idx_t)localBot, oldAge.tag() + 1);
-  // Perhaps a competing pop_global has already incremented "top", in which
-  // case it wins the element.
-  if (localBot == oldAge.top()) {
-    // No competing pop_global has yet incremented "top"; we'll try to
-    // install new_age, thus claiming the element.
-    Age tempAge = _age.cmpxchg(newAge, oldAge);
-    if (tempAge == oldAge) {
-      // We win.
-      assert(dirty_size(localBot, _age.top()) != N - 1, "sanity");
-      TASKQUEUE_STATS_ONLY(stats.record_pop_slow());
-      return true;
-    }
-  }
-  // We lose; a completing pop_global gets the element.  But the queue is empty
-  // and top is greater than bottom.  Fix this representation of the empty queue
-  // to become the canonical one.
-  _age.set(newAge);
-  assert(dirty_size(localBot, _age.top()) != N - 1, "sanity");
-  return false;
-}
-
-template<class E, MEMFLAGS F, unsigned int N>
-bool GenericTaskQueue<E, F, N>::pop_global(volatile E& t) {
-  Age oldAge = _age.get();
-  // Architectures with weak memory model require a barrier here
-  // to guarantee that bottom is not older than age,
-  // which is crucial for the correctness of the algorithm.
-#if !(defined SPARC || defined IA32 || defined AMD64)
-  OrderAccess::fence();
-#endif
-  uint localBot = OrderAccess::load_acquire((volatile juint*)&_bottom);
-  uint n_elems = size(localBot, oldAge.top());
-  if (n_elems == 0) {
-    return false;
-  }
-
-  // g++ complains if the volatile result of the assignment is
-  // unused, so we cast the volatile away.  We cannot cast directly
-  // to void, because gcc treats that as not using the result of the
-  // assignment.  However, casting to E& means that we trigger an
-  // unused-value warning.  So, we cast the E& to void.
-  (void) const_cast<E&>(t = _elems[oldAge.top()]);
-  Age newAge(oldAge);
-  newAge.increment();
-  Age resAge = _age.cmpxchg(newAge, oldAge);
-
-  // Note that using "_bottom" here might fail, since a pop_local might
-  // have decremented it.
-  assert(dirty_size(localBot, newAge.top()) != N - 1, "sanity");
-  return resAge == oldAge;
-}
-
-template<class E, MEMFLAGS F, unsigned int N>
-GenericTaskQueue<E, F, N>::~GenericTaskQueue() {
-  FREE_C_HEAP_ARRAY(E, _elems);
-}
-
 // OverflowTaskQueue is a TaskQueue that also includes an overflow stack for
 // elements that do not fit in the TaskQueue.
 //
@@ -468,24 +346,6 @@
   overflow_t _overflow_stack;
 };
 
-template <class E, MEMFLAGS F, unsigned int N>
-bool OverflowTaskQueue<E, F, N>::push(E t)
-{
-  if (!taskqueue_t::push(t)) {
-    overflow_stack()->push(t);
-    TASKQUEUE_STATS_ONLY(stats.record_overflow(overflow_stack()->size()));
-  }
-  return true;
-}
-
-template <class E, MEMFLAGS F, unsigned int N>
-bool OverflowTaskQueue<E, F, N>::pop_overflow(E& t)
-{
-  if (overflow_empty()) return false;
-  t = overflow_stack()->pop();
-  return true;
-}
-
 class TaskQueueSetSuper {
 protected:
   static int randomParkAndMiller(int* seed0);
@@ -506,13 +366,7 @@
 public:
   typedef typename T::element_type E;
 
-  GenericTaskQueueSet(int n) : _n(n) {
-    typedef T* GenericTaskQueuePtr;
-    _queues = NEW_C_HEAP_ARRAY(GenericTaskQueuePtr, n, F);
-    for (int i = 0; i < n; i++) {
-      _queues[i] = NULL;
-    }
-  }
+  GenericTaskQueueSet(int n);
 
   bool steal_best_of_2(uint queue_num, int* seed, E& t);
 
@@ -541,40 +395,6 @@
   return _queues[i];
 }
 
-template<class T, MEMFLAGS F> bool
-GenericTaskQueueSet<T, F>::steal(uint queue_num, int* seed, E& t) {
-  for (uint i = 0; i < 2 * _n; i++) {
-    if (steal_best_of_2(queue_num, seed, t)) {
-      TASKQUEUE_STATS_ONLY(queue(queue_num)->stats.record_steal(true));
-      return true;
-    }
-  }
-  TASKQUEUE_STATS_ONLY(queue(queue_num)->stats.record_steal(false));
-  return false;
-}
-
-template<class T, MEMFLAGS F> bool
-GenericTaskQueueSet<T, F>::steal_best_of_2(uint queue_num, int* seed, E& t) {
-  if (_n > 2) {
-    uint k1 = queue_num;
-    while (k1 == queue_num) k1 = TaskQueueSetSuper::randomParkAndMiller(seed) % _n;
-    uint k2 = queue_num;
-    while (k2 == queue_num || k2 == k1) k2 = TaskQueueSetSuper::randomParkAndMiller(seed) % _n;
-    // Sample both and try the larger.
-    uint sz1 = _queues[k1]->size();
-    uint sz2 = _queues[k2]->size();
-    if (sz2 > sz1) return _queues[k2]->pop_global(t);
-    else return _queues[k1]->pop_global(t);
-  } else if (_n == 2) {
-    // Just try the other one.
-    uint k = (queue_num + 1) % 2;
-    return _queues[k]->pop_global(t);
-  } else {
-    assert(_n == 1, "can't be zero.");
-    return false;
-  }
-}
-
 template<class T, MEMFLAGS F>
 bool GenericTaskQueueSet<T, F>::peek() {
   // Try all the queues.
@@ -598,9 +418,9 @@
 
 class ParallelTaskTerminator: public StackObj {
 private:
-  int _n_threads;
+  uint _n_threads;
   TaskQueueSetSuper* _queue_set;
-  int _offered_termination;
+  uint _offered_termination;
 
 #ifdef TRACESPINNING
   static uint _total_yields;
@@ -617,7 +437,7 @@
 
   // "n_threads" is the number of threads to be terminated.  "queue_set" is a
   // queue sets of work queues of other threads.
-  ParallelTaskTerminator(int n_threads, TaskQueueSetSuper* queue_set);
+  ParallelTaskTerminator(uint n_threads, TaskQueueSetSuper* queue_set);
 
   // The current thread has no work, and is ready to terminate if everyone
   // else is.  If returns "true", all threads are terminated.  If returns
@@ -639,7 +459,7 @@
   void reset_for_reuse();
   // Same as above but the number of parallel threads is set to the
   // given number.
-  void reset_for_reuse(int n_threads);
+  void reset_for_reuse(uint n_threads);
 
 #ifdef TRACESPINNING
   static uint total_yields() { return _total_yields; }
@@ -649,65 +469,6 @@
 #endif
 };
 
-template<class E, MEMFLAGS F, unsigned int N> inline bool
-GenericTaskQueue<E, F, N>::push(E t) {
-  uint localBot = _bottom;
-  assert(localBot < N, "_bottom out of range.");
-  idx_t top = _age.top();
-  uint dirty_n_elems = dirty_size(localBot, top);
-  assert(dirty_n_elems < N, "n_elems out of range.");
-  if (dirty_n_elems < max_elems()) {
-    // g++ complains if the volatile result of the assignment is
-    // unused, so we cast the volatile away.  We cannot cast directly
-    // to void, because gcc treats that as not using the result of the
-    // assignment.  However, casting to E& means that we trigger an
-    // unused-value warning.  So, we cast the E& to void.
-    (void) const_cast<E&>(_elems[localBot] = t);
-    OrderAccess::release_store(&_bottom, increment_index(localBot));
-    TASKQUEUE_STATS_ONLY(stats.record_push());
-    return true;
-  } else {
-    return push_slow(t, dirty_n_elems);
-  }
-}
-
-template<class E, MEMFLAGS F, unsigned int N> inline bool
-GenericTaskQueue<E, F, N>::pop_local(volatile E& t) {
-  uint localBot = _bottom;
-  // This value cannot be N-1.  That can only occur as a result of
-  // the assignment to bottom in this method.  If it does, this method
-  // resets the size to 0 before the next call (which is sequential,
-  // since this is pop_local.)
-  uint dirty_n_elems = dirty_size(localBot, _age.top());
-  assert(dirty_n_elems != N - 1, "Shouldn't be possible...");
-  if (dirty_n_elems == 0) return false;
-  localBot = decrement_index(localBot);
-  _bottom = localBot;
-  // This is necessary to prevent any read below from being reordered
-  // before the store just above.
-  OrderAccess::fence();
-  // g++ complains if the volatile result of the assignment is
-  // unused, so we cast the volatile away.  We cannot cast directly
-  // to void, because gcc treats that as not using the result of the
-  // assignment.  However, casting to E& means that we trigger an
-  // unused-value warning.  So, we cast the E& to void.
-  (void) const_cast<E&>(t = _elems[localBot]);
-  // This is a second read of "age"; the "size()" above is the first.
-  // If there's still at least one element in the queue, based on the
-  // "_bottom" and "age" we've read, then there can be no interference with
-  // a "pop_global" operation, and we're done.
-  idx_t tp = _age.top();    // XXX
-  if (size(localBot, tp) > 0) {
-    assert(dirty_size(localBot, tp) != N - 1, "sanity");
-    TASKQUEUE_STATS_ONLY(stats.record_pop());
-    return true;
-  } else {
-    // Otherwise, the queue contained exactly one element; we take the slow
-    // path.
-    return pop_local_slow(localBot, _age.get());
-  }
-}
-
 typedef GenericTaskQueue<oop, mtGC>             OopTaskQueue;
 typedef GenericTaskQueueSet<OopTaskQueue, mtGC> OopTaskQueueSet;
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/src/share/vm/utilities/taskqueue.inline.hpp	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,279 @@
+/*
+ * 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_TASKQUEUE_INLINE_HPP
+#define SHARE_VM_UTILITIES_TASKQUEUE_INLINE_HPP
+
+#include "memory/allocation.inline.hpp"
+#include "oops/oop.inline.hpp"
+#include "utilities/debug.hpp"
+#include "utilities/taskqueue.hpp"
+#include "utilities/stack.inline.hpp"
+#include "runtime/atomic.inline.hpp"
+#include "runtime/orderAccess.inline.hpp"
+
+template <class T, MEMFLAGS F>
+inline GenericTaskQueueSet<T, F>::GenericTaskQueueSet(int n) : _n(n) {
+  typedef T* GenericTaskQueuePtr;
+  _queues = NEW_C_HEAP_ARRAY(GenericTaskQueuePtr, n, F);
+  for (int i = 0; i < n; i++) {
+    _queues[i] = NULL;
+  }
+}
+
+template<class E, MEMFLAGS F, unsigned int N>
+inline void GenericTaskQueue<E, F, N>::initialize() {
+  _elems = _array_allocator.allocate(N);
+}
+
+template<class E, MEMFLAGS F, unsigned int N>
+inline GenericTaskQueue<E, F, N>::~GenericTaskQueue() {
+  FREE_C_HEAP_ARRAY(E, _elems);
+}
+
+template<class E, MEMFLAGS F, unsigned int N>
+bool GenericTaskQueue<E, F, N>::push_slow(E t, uint dirty_n_elems) {
+  if (dirty_n_elems == N - 1) {
+    // Actually means 0, so do the push.
+    uint localBot = _bottom;
+    // g++ complains if the volatile result of the assignment is
+    // unused, so we cast the volatile away.  We cannot cast directly
+    // to void, because gcc treats that as not using the result of the
+    // assignment.  However, casting to E& means that we trigger an
+    // unused-value warning.  So, we cast the E& to void.
+    (void)const_cast<E&>(_elems[localBot] = t);
+    OrderAccess::release_store(&_bottom, increment_index(localBot));
+    TASKQUEUE_STATS_ONLY(stats.record_push());
+    return true;
+  }
+  return false;
+}
+
+template<class E, MEMFLAGS F, unsigned int N> inline bool
+GenericTaskQueue<E, F, N>::push(E t) {
+  uint localBot = _bottom;
+  assert(localBot < N, "_bottom out of range.");
+  idx_t top = _age.top();
+  uint dirty_n_elems = dirty_size(localBot, top);
+  assert(dirty_n_elems < N, "n_elems out of range.");
+  if (dirty_n_elems < max_elems()) {
+    // g++ complains if the volatile result of the assignment is
+    // unused, so we cast the volatile away.  We cannot cast directly
+    // to void, because gcc treats that as not using the result of the
+    // assignment.  However, casting to E& means that we trigger an
+    // unused-value warning.  So, we cast the E& to void.
+    (void) const_cast<E&>(_elems[localBot] = t);
+    OrderAccess::release_store(&_bottom, increment_index(localBot));
+    TASKQUEUE_STATS_ONLY(stats.record_push());
+    return true;
+  } else {
+    return push_slow(t, dirty_n_elems);
+  }
+}
+
+template <class E, MEMFLAGS F, unsigned int N>
+inline bool OverflowTaskQueue<E, F, N>::push(E t)
+{
+  if (!taskqueue_t::push(t)) {
+    overflow_stack()->push(t);
+    TASKQUEUE_STATS_ONLY(stats.record_overflow(overflow_stack()->size()));
+  }
+  return true;
+}
+
+// pop_local_slow() is done by the owning thread and is trying to
+// get the last task in the queue.  It will compete with pop_global()
+// that will be used by other threads.  The tag age is incremented
+// whenever the queue goes empty which it will do here if this thread
+// gets the last task or in pop_global() if the queue wraps (top == 0
+// and pop_global() succeeds, see pop_global()).
+template<class E, MEMFLAGS F, unsigned int N>
+bool GenericTaskQueue<E, F, N>::pop_local_slow(uint localBot, Age oldAge) {
+  // This queue was observed to contain exactly one element; either this
+  // thread will claim it, or a competing "pop_global".  In either case,
+  // the queue will be logically empty afterwards.  Create a new Age value
+  // that represents the empty queue for the given value of "_bottom".  (We
+  // must also increment "tag" because of the case where "bottom == 1",
+  // "top == 0".  A pop_global could read the queue element in that case,
+  // then have the owner thread do a pop followed by another push.  Without
+  // the incrementing of "tag", the pop_global's CAS could succeed,
+  // allowing it to believe it has claimed the stale element.)
+  Age newAge((idx_t)localBot, oldAge.tag() + 1);
+  // Perhaps a competing pop_global has already incremented "top", in which
+  // case it wins the element.
+  if (localBot == oldAge.top()) {
+    // No competing pop_global has yet incremented "top"; we'll try to
+    // install new_age, thus claiming the element.
+    Age tempAge = _age.cmpxchg(newAge, oldAge);
+    if (tempAge == oldAge) {
+      // We win.
+      assert(dirty_size(localBot, _age.top()) != N - 1, "sanity");
+      TASKQUEUE_STATS_ONLY(stats.record_pop_slow());
+      return true;
+    }
+  }
+  // We lose; a completing pop_global gets the element.  But the queue is empty
+  // and top is greater than bottom.  Fix this representation of the empty queue
+  // to become the canonical one.
+  _age.set(newAge);
+  assert(dirty_size(localBot, _age.top()) != N - 1, "sanity");
+  return false;
+}
+
+template<class E, MEMFLAGS F, unsigned int N> inline bool
+GenericTaskQueue<E, F, N>::pop_local(volatile E& t) {
+  uint localBot = _bottom;
+  // This value cannot be N-1.  That can only occur as a result of
+  // the assignment to bottom in this method.  If it does, this method
+  // resets the size to 0 before the next call (which is sequential,
+  // since this is pop_local.)
+  uint dirty_n_elems = dirty_size(localBot, _age.top());
+  assert(dirty_n_elems != N - 1, "Shouldn't be possible...");
+  if (dirty_n_elems == 0) return false;
+  localBot = decrement_index(localBot);
+  _bottom = localBot;
+  // This is necessary to prevent any read below from being reordered
+  // before the store just above.
+  OrderAccess::fence();
+  // g++ complains if the volatile result of the assignment is
+  // unused, so we cast the volatile away.  We cannot cast directly
+  // to void, because gcc treats that as not using the result of the
+  // assignment.  However, casting to E& means that we trigger an
+  // unused-value warning.  So, we cast the E& to void.
+  (void) const_cast<E&>(t = _elems[localBot]);
+  // This is a second read of "age"; the "size()" above is the first.
+  // If there's still at least one element in the queue, based on the
+  // "_bottom" and "age" we've read, then there can be no interference with
+  // a "pop_global" operation, and we're done.
+  idx_t tp = _age.top();    // XXX
+  if (size(localBot, tp) > 0) {
+    assert(dirty_size(localBot, tp) != N - 1, "sanity");
+    TASKQUEUE_STATS_ONLY(stats.record_pop());
+    return true;
+  } else {
+    // Otherwise, the queue contained exactly one element; we take the slow
+    // path.
+    return pop_local_slow(localBot, _age.get());
+  }
+}
+
+template <class E, MEMFLAGS F, unsigned int N>
+bool OverflowTaskQueue<E, F, N>::pop_overflow(E& t)
+{
+  if (overflow_empty()) return false;
+  t = overflow_stack()->pop();
+  return true;
+}
+
+template<class E, MEMFLAGS F, unsigned int N>
+bool GenericTaskQueue<E, F, N>::pop_global(volatile E& t) {
+  Age oldAge = _age.get();
+  // Architectures with weak memory model require a barrier here
+  // to guarantee that bottom is not older than age,
+  // which is crucial for the correctness of the algorithm.
+#if !(defined SPARC || defined IA32 || defined AMD64)
+  OrderAccess::fence();
+#endif
+  uint localBot = OrderAccess::load_acquire((volatile juint*)&_bottom);
+  uint n_elems = size(localBot, oldAge.top());
+  if (n_elems == 0) {
+    return false;
+  }
+
+  // g++ complains if the volatile result of the assignment is
+  // unused, so we cast the volatile away.  We cannot cast directly
+  // to void, because gcc treats that as not using the result of the
+  // assignment.  However, casting to E& means that we trigger an
+  // unused-value warning.  So, we cast the E& to void.
+  (void) const_cast<E&>(t = _elems[oldAge.top()]);
+  Age newAge(oldAge);
+  newAge.increment();
+  Age resAge = _age.cmpxchg(newAge, oldAge);
+
+  // Note that using "_bottom" here might fail, since a pop_local might
+  // have decremented it.
+  assert(dirty_size(localBot, newAge.top()) != N - 1, "sanity");
+  return resAge == oldAge;
+}
+
+template<class T, MEMFLAGS F> bool
+GenericTaskQueueSet<T, F>::steal_best_of_2(uint queue_num, int* seed, E& t) {
+  if (_n > 2) {
+    uint k1 = queue_num;
+    while (k1 == queue_num) k1 = TaskQueueSetSuper::randomParkAndMiller(seed) % _n;
+    uint k2 = queue_num;
+    while (k2 == queue_num || k2 == k1) k2 = TaskQueueSetSuper::randomParkAndMiller(seed) % _n;
+    // Sample both and try the larger.
+    uint sz1 = _queues[k1]->size();
+    uint sz2 = _queues[k2]->size();
+    if (sz2 > sz1) return _queues[k2]->pop_global(t);
+    else return _queues[k1]->pop_global(t);
+  } else if (_n == 2) {
+    // Just try the other one.
+    uint k = (queue_num + 1) % 2;
+    return _queues[k]->pop_global(t);
+  } else {
+    assert(_n == 1, "can't be zero.");
+    return false;
+  }
+}
+
+template<class T, MEMFLAGS F> bool
+GenericTaskQueueSet<T, F>::steal(uint queue_num, int* seed, E& t) {
+  for (uint i = 0; i < 2 * _n; i++) {
+    if (steal_best_of_2(queue_num, seed, t)) {
+      TASKQUEUE_STATS_ONLY(queue(queue_num)->stats.record_steal(true));
+      return true;
+    }
+  }
+  TASKQUEUE_STATS_ONLY(queue(queue_num)->stats.record_steal(false));
+  return false;
+}
+
+template <unsigned int N, MEMFLAGS F>
+inline typename TaskQueueSuper<N, F>::Age TaskQueueSuper<N, F>::Age::cmpxchg(const Age new_age, const Age old_age) volatile {
+  return (size_t) Atomic::cmpxchg_ptr((intptr_t)new_age._data,
+                                      (volatile intptr_t *)&_data,
+                                      (intptr_t)old_age._data);
+}
+
+template<class E, MEMFLAGS F, unsigned int N>
+inline void GenericTaskQueue<E, F, N>::oops_do(OopClosure* f) {
+  // tty->print_cr("START OopTaskQueue::oops_do");
+  uint iters = size();
+  uint index = _bottom;
+  for (uint i = 0; i < iters; ++i) {
+    index = decrement_index(index);
+    // tty->print_cr("  doing entry %d," INTPTR_T " -> " INTPTR_T,
+    //            index, &_elems[index], _elems[index]);
+    E* t = (E*)&_elems[index];      // cast away volatility
+    oop* p = (oop*)t;
+    assert((*t)->is_oop_or_null(), err_msg("Expected an oop or NULL at " PTR_FORMAT, p2i(*t)));
+    f->do_oop(p);
+  }
+  // tty->print_cr("END OopTaskQueue::oops_do");
+}
+
+
+#endif // SHARE_VM_UTILITIES_TASKQUEUE_INLINE_HPP
--- a/hotspot/src/share/vm/utilities/vmError.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/utilities/vmError.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -520,7 +520,7 @@
     st->print("# ");
     if (CreateCoredumpOnCrash) {
       if (coredump_status) {
-        st->print("Core dump will be written. %s", coredump_message);
+        st->print("Core dump will be written. Default location: %s", coredump_message);
       } else {
         st->print("No core dump will be written. %s", coredump_message);
       }
--- a/hotspot/src/share/vm/utilities/workgroup.cpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/utilities/workgroup.cpp	Wed Jul 05 20:35:10 2017 +0200
@@ -29,8 +29,6 @@
 #include "runtime/os.hpp"
 #include "utilities/workgroup.hpp"
 
-PRAGMA_FORMAT_MUTE_WARNINGS_FOR_GCC
-
 // Definitions of WorkGang methods.
 
 AbstractWorkGang::AbstractWorkGang(const char* name,
@@ -155,7 +153,7 @@
   // Wait for them to be finished
   while (finished_workers() < no_of_parallel_workers) {
     if (TraceWorkGang) {
-      tty->print_cr("Waiting in work gang %s: %d/%d finished sequence %d",
+      tty->print_cr("Waiting in work gang %s: %u/%u finished sequence %d",
                     name(), finished_workers(), no_of_parallel_workers,
                     _sequence_number);
     }
@@ -163,11 +161,11 @@
   }
   _task = NULL;
   if (TraceWorkGang) {
-    tty->print_cr("\nFinished work gang %s: %d/%d sequence %d",
+    tty->print_cr("\nFinished work gang %s: %u/%u sequence %d",
                   name(), finished_workers(), no_of_parallel_workers,
                   _sequence_number);
     Thread* me = Thread::current();
-    tty->print_cr("  T: 0x%x  VM_thread: %d", me, me->is_VM_thread());
+    tty->print_cr("  T: " PTR_FORMAT "  VM_thread: %d", p2i(me), me->is_VM_thread());
   }
 }
 
@@ -190,7 +188,7 @@
   monitor()->notify_all();
   while (finished_workers() < active_workers()) {
     if (TraceWorkGang) {
-      tty->print_cr("Waiting in work gang %s: %d/%d finished",
+      tty->print_cr("Waiting in work gang %s: %u/%u finished",
                     name(), finished_workers(), active_workers());
     }
     monitor()->wait(/* no_safepoint_check */ true);
@@ -251,7 +249,7 @@
   assert(_gang != NULL, "No gang to run in");
   os::set_priority(this, NearMaxPriority);
   if (TraceWorkGang) {
-    tty->print_cr("Running gang worker for gang %s id %d",
+    tty->print_cr("Running gang worker for gang %s id %u",
                   gang()->name(), id());
   }
   // The VM thread should not execute here because MutexLocker's are used
@@ -274,7 +272,7 @@
       // in the outer loop.
       gang()->internal_worker_poll(&data);
       if (TraceWorkGang) {
-        tty->print("Polled outside for work in gang %s worker %d",
+        tty->print("Polled outside for work in gang %s worker %u",
                    gang()->name(), id());
         tty->print("  terminate: %s",
                    data.terminate() ? "true" : "false");
@@ -308,7 +306,7 @@
         gang_monitor->wait(/* no_safepoint_check */ true);
         gang()->internal_worker_poll(&data);
         if (TraceWorkGang) {
-          tty->print("Polled inside for work in gang %s worker %d",
+          tty->print("Polled inside for work in gang %s worker %u",
                      gang()->name(), id());
           tty->print("  terminate: %s",
                      data.terminate() ? "true" : "false");
@@ -325,14 +323,14 @@
       // Drop gang mutex.
     }
     if (TraceWorkGang) {
-      tty->print("Work for work gang %s id %d task %s part %d",
+      tty->print("Work for work gang %s id %u task %s part %d",
                  gang()->name(), id(), data.task()->name(), part);
     }
     assert(data.task() != NULL, "Got null task");
     data.task()->work(part);
     {
       if (TraceWorkGang) {
-        tty->print("Finish for work gang %s id %d task %s part %d",
+        tty->print("Finish for work gang %s id %u task %s part %d",
                    gang()->name(), id(), data.task()->name(), part);
       }
       // Grab the gang mutex.
--- a/hotspot/src/share/vm/utilities/workgroup.hpp	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/src/share/vm/utilities/workgroup.hpp	Wed Jul 05 20:35:10 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
@@ -64,7 +64,7 @@
   // and may inherit this method that does nothing.  Some
   // tasks do some coordination on termination and override
   // this method to implement that coordination.
-  virtual void set_for_termination(int active_workers) {};
+  virtual void set_for_termination(uint active_workers) {};
 
   // Debugging accessor for the name.
   const char* name() const PRODUCT_RETURN_(return NULL;);
@@ -102,7 +102,7 @@
   AbstractGangTaskWOopQueues(const char* name, OopTaskQueueSet* queues) :
     AbstractGangTask(name), _queues(queues), _terminator(0, _queues) {}
   ParallelTaskTerminator* terminator() { return &_terminator; }
-  virtual void set_for_termination(int active_workers) {
+  virtual void set_for_termination(uint active_workers) {
     terminator()->reset_for_reuse(active_workers);
   }
   OopTaskQueueSet* queues() { return _queues; }
--- a/hotspot/test/Makefile	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/Makefile	Wed Jul 05 20:35:10 2017 +0200
@@ -28,8 +28,6 @@
 
 ALT_MAKE ?= closed
 
--include $(ALT_MAKE)/Makefile
-
 GETMIXEDPATH=echo
 
 # Utilities used
@@ -306,6 +304,8 @@
 endif
 JTREG_BASIC_OPTIONS += $(JTREG_KEY_OPTION)
 
+-include $(ALT_MAKE)/Makefile
+
 # Make sure jtreg exists
 $(JTREG): $(JT_HOME)
 
@@ -368,6 +368,10 @@
 	for variant in $(JVM_VARIANTS);                                           \
 	do                                                                        \
 	    $(MAKE) JAVA_ARGS="$(JAVA_ARGS) -$$variant" hotspot_$${variant}test;  \
+	    res=$$?;                                                              \
+	    if [ $$res -ne 0 ]; then                                              \
+	        exit $$res;                                                       \
+	    fi;                                                                   \
 	done
 
 PHONY_LIST += hotspot_basicvmtest
@@ -401,15 +405,6 @@
 
 ################################################################
 
-# internalvmtests (run internal unit tests inside the VM)
-
-hotspot_internalvmtests internalvmtests: prep $(PRODUCT_HOME)
-	$(PRODUCT_HOME)/bin/java $(JAVA_OPTIONS) -XX:+ExecuteInternalVMTests -version
-
-PHONY_LIST += hotspot_internalvmtests internalvmtests
-
-################################################################
-
 # Phony targets (e.g. these are not filenames)
 .PHONY: all clean prep $(PHONY_LIST)
 
--- a/hotspot/test/TEST.groups	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/TEST.groups	Wed Jul 05 20:35:10 2017 +0200
@@ -233,6 +233,7 @@
   gc/arguments/TestParallelGCThreads.java \
   gc/arguments/TestUseCompressedOopsErgo.java \
   gc/class_unloading/TestG1ClassUnloadingHWM.java \
+  gc/ergonomics/TestDynamicNumberOfGCThreads.java
   gc/g1/ \
   gc/metaspace/G1AddMetaspaceDependency.java \
   gc/metaspace/TestMetaspacePerfCounters.java \
@@ -262,6 +263,7 @@
   gc/arguments/TestMinInitialErgonomics.java \
   gc/arguments/TestParallelGCThreads.java \
   gc/arguments/TestUseCompressedOopsErgo.java \
+  gc/ergonomics/TestDynamicNumberOfGCThreads.java
   gc/metaspace/TestMetaspacePerfCounters.java \
   gc/parallelScavenge/ \
   gc/startup_warnings/TestParallelGC.java \
@@ -279,6 +281,7 @@
   gc/arguments/TestUseCompressedOopsErgo.java \
   gc/class_unloading/TestCMSClassUnloadingEnabledHWM.java \
   gc/concurrentMarkSweep/ \
+  gc/ergonomics/TestDynamicNumberOfGCThreads.java
   gc/startup_warnings/TestCMS.java \
   gc/startup_warnings/TestDefNewCMS.java \
   gc/startup_warnings/TestParNewCMS.java
@@ -329,11 +332,6 @@
  -:needs_serialgc \
  -:needs_parallelgc
 
-
-# When called from top level the test suites use the hotspot_ prefix
-hotspot_wbapitest = \
-  sanity/
-
 hotspot_native_sanity = \
   native_sanity
 
@@ -418,7 +416,7 @@
  -runtime/SharedArchiveFile/DefaultUseWithClient.java \
  -runtime/Thread/CancellableThreadTest.java \
  -runtime/7158988/FieldMonitor.java \
-  sanity/ExecuteInternalVMTests.java \
+  sanity/ \
   testlibrary_tests/TestMutuallyExclusivePlatformPredicates.java
 
 hotspot_serviceability = \
@@ -426,7 +424,6 @@
   serviceability/dcmd/compiler
 
 hotspot_jprt = \
-  :hotspot_wbapitest \
   :hotspot_compiler_1 \
   :hotspot_compiler_2 \
   :hotspot_compiler_3 \
@@ -435,7 +432,6 @@
   :hotspot_gc_closed \
   :hotspot_gc_gcold \
   :hotspot_runtime \
-  :hotspot_runtime_closed \
   :hotspot_serviceability
 
 #All tests that depends on nashorn extension.
--- a/hotspot/test/compiler/arguments/BMICommandLineOptionTestBase.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/arguments/BMICommandLineOptionTestBase.java	Wed Jul 05 20:35:10 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
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.cli.*;
+import jdk.test.lib.cli.*;
 
 /**
  * Base class for all X86 bit manipulation related command line options.
--- a/hotspot/test/compiler/arguments/BMISupportedCPUTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/arguments/BMISupportedCPUTest.java	Wed Jul 05 20:35:10 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
@@ -21,8 +21,8 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.*;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.*;
 
 /**
  * Test on bit manipulation related command line options,
--- a/hotspot/test/compiler/arguments/BMIUnsupportedCPUTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/arguments/BMIUnsupportedCPUTest.java	Wed Jul 05 20:35:10 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
@@ -21,8 +21,8 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.*;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.*;
 
 /**
  * Test on bit manipulation related command line options,
--- a/hotspot/test/compiler/arguments/CheckCompileThresholdScaling.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/arguments/CheckCompileThresholdScaling.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 /*
  * @test CheckCompileThresholdScaling
--- a/hotspot/test/compiler/arguments/TestUseBMI1InstructionsOnSupportedCPU.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/arguments/TestUseBMI1InstructionsOnSupportedCPU.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,7 +38,7 @@
  */
 
 import sun.hotspot.cpuinfo.CPUInfo;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class TestUseBMI1InstructionsOnSupportedCPU
      extends BMISupportedCPUTest {
--- a/hotspot/test/compiler/arguments/TestUseBMI1InstructionsOnUnsupportedCPU.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/arguments/TestUseBMI1InstructionsOnUnsupportedCPU.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,8 +38,8 @@
  */
 
 import sun.hotspot.cpuinfo.CPUInfo;
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.*;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.*;
 
 public class TestUseBMI1InstructionsOnUnsupportedCPU
       extends BMIUnsupportedCPUTest {
--- a/hotspot/test/compiler/arguments/TestUseCountLeadingZerosInstructionOnSupportedCPU.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/arguments/TestUseCountLeadingZerosInstructionOnSupportedCPU.java	Wed Jul 05 20:35:10 2017 +0200
@@ -39,7 +39,7 @@
  */
 
 import sun.hotspot.cpuinfo.CPUInfo;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class TestUseCountLeadingZerosInstructionOnSupportedCPU
      extends BMISupportedCPUTest {
--- a/hotspot/test/compiler/arguments/TestUseCountLeadingZerosInstructionOnUnsupportedCPU.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/arguments/TestUseCountLeadingZerosInstructionOnUnsupportedCPU.java	Wed Jul 05 20:35:10 2017 +0200
@@ -39,7 +39,7 @@
  */
 
 import sun.hotspot.cpuinfo.CPUInfo;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class TestUseCountLeadingZerosInstructionOnUnsupportedCPU
      extends BMIUnsupportedCPUTest {
--- a/hotspot/test/compiler/arguments/TestUseCountTrailingZerosInstructionOnSupportedCPU.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/arguments/TestUseCountTrailingZerosInstructionOnSupportedCPU.java	Wed Jul 05 20:35:10 2017 +0200
@@ -39,8 +39,8 @@
  */
 
 import sun.hotspot.cpuinfo.CPUInfo;
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.*;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.*;
 
 public class TestUseCountTrailingZerosInstructionOnSupportedCPU
         extends BMISupportedCPUTest {
--- a/hotspot/test/compiler/arguments/TestUseCountTrailingZerosInstructionOnUnsupportedCPU.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/arguments/TestUseCountTrailingZerosInstructionOnUnsupportedCPU.java	Wed Jul 05 20:35:10 2017 +0200
@@ -39,8 +39,8 @@
  */
 
 import sun.hotspot.cpuinfo.CPUInfo;
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.*;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.*;
 
 public class TestUseCountTrailingZerosInstructionOnUnsupportedCPU
         extends BMIUnsupportedCPUTest {
--- a/hotspot/test/compiler/arraycopy/TestArrayCopyAsLoadsStores.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/arraycopy/TestArrayCopyAsLoadsStores.java	Wed Jul 05 20:35:10 2017 +0200
@@ -25,50 +25,15 @@
  * @test
  * @bug 6912521
  * @summary small array copy as loads/stores
+ * @compile TestArrayCopyAsLoadsStores.java TestArrayCopyUtils.java
  * @run main/othervm -ea -XX:-BackgroundCompilation -XX:-UseOnStackReplacement -XX:CompileCommand=dontinline,TestArrayCopyAsLoadsStores::m* -XX:TypeProfileLevel=200 TestArrayCopyAsLoadsStores
  * @run main/othervm -ea -XX:-BackgroundCompilation -XX:-UseOnStackReplacement -XX:CompileCommand=dontinline,TestArrayCopyAsLoadsStores::m* -XX:+IgnoreUnrecognizedVMOptions -XX:+StressArrayCopyMacroNode -XX:TypeProfileLevel=200 TestArrayCopyAsLoadsStores
  *
  */
 
-import java.lang.annotation.*;
-import java.lang.reflect.*;
 import java.util.*;
 
-public class TestArrayCopyAsLoadsStores {
-
-    public enum ArraySrc {
-        SMALL,
-        LARGE,
-        ZERO
-    }
-
-    public enum ArrayDst {
-        NONE,
-        NEW,
-        SRC
-    }
-
-    static class A {
-    }
-
-    static class B extends A {
-    }
-
-    static final A[] small_a_src = new A[5];
-    static final A[] large_a_src = new A[10];
-    static final A[] zero_a_src = new A[0];
-    static final int[] small_int_src = new int[5];
-    static final int[] large_int_src = new int[10];
-    static final int[] zero_int_src = new int[0];
-    static final Object[] small_object_src = new Object[5];
-    static Object src;
-
-    @Retention(RetentionPolicy.RUNTIME)
-    @interface Args {
-        ArraySrc src();
-        ArrayDst dst() default ArrayDst.NONE;
-        int[] extra_args() default {};
-    }
+public class TestArrayCopyAsLoadsStores extends TestArrayCopyUtils {
 
     // array clone should be compiled as loads/stores
     @Args(src=ArraySrc.SMALL)
@@ -349,166 +314,7 @@
         return false;
     }
 
-    final HashMap<String,Method> tests = new HashMap<>();
-    {
-        for (Method m : this.getClass().getDeclaredMethods()) {
-            if (m.getName().matches("m[0-9]+(_check)?")) {
-                assert(Modifier.isStatic(m.getModifiers())) : m;
-                tests.put(m.getName(), m);
-            }
-        }
-    }
-
-    boolean success = true;
-
-    void doTest(String name) throws Exception {
-        Method m = tests.get(name);
-        Method m_check = tests.get(name + "_check");
-        Class[] paramTypes = m.getParameterTypes();
-        Object[] params = new Object[paramTypes.length];
-        Class retType = m.getReturnType();
-        boolean isIntArray = (retType.isPrimitive() && !retType.equals(Void.TYPE)) ||
-            (retType.equals(Void.TYPE) && paramTypes[0].getComponentType().isPrimitive()) ||
-            (retType.isArray() && retType.getComponentType().isPrimitive());
-
-        Args args = m.getAnnotation(Args.class);
-
-        Object src = null;
-        switch(args.src()) {
-        case SMALL: {
-            if (isIntArray) {
-                src = small_int_src;
-            } else {
-                src = small_a_src;
-            }
-            break;
-        }
-        case LARGE: {
-            if (isIntArray) {
-                src = large_int_src;
-            } else {
-                src = large_a_src;
-            }
-            break;
-        }
-        case ZERO: {
-            if (isIntArray) {
-                src = zero_int_src;
-            } else {
-                src = zero_a_src;
-            }
-            break;
-        }
-        }
-
-        for (int i = 0; i < 20000; i++) {
-            boolean failure = false;
-
-            int p = 0;
-
-            if (params.length > 0) {
-                if (isIntArray) {
-                    params[0] = ((int[])src).clone();
-                } else {
-                    params[0] = ((A[])src).clone();
-                }
-                p++;
-            }
-
-            if (params.length > 1) {
-                switch(args.dst()) {
-                case NEW: {
-                    if (isIntArray) {
-                        params[1] = new int[((int[])params[0]).length];
-                    } else {
-                        params[1] = new A[((A[])params[0]).length];
-                    }
-                    p++;
-                    break;
-                }
-                case SRC: {
-                    params[1] = params[0];
-                    p++;
-                    break;
-                }
-                case NONE: break;
-                }
-            }
-
-            for (int j = 0; j < args.extra_args().length; j++) {
-                params[p+j] = args.extra_args()[j];
-            }
-
-            Object res = m.invoke(null, params);
-
-            if (retType.isPrimitive() && !retType.equals(Void.TYPE)) {
-                int s = (int)res;
-                int sum = 0;
-                int[] int_res = (int[])src;
-                for (int j = 0; j < int_res.length; j++) {
-                    sum += int_res[j];
-                }
-                failure = (s != sum);
-                if (failure) {
-                    System.out.println("Test " + name + " failed: result = " + s + " != " + sum);
-                }
-            } else {
-                Object dest = null;
-                if (!retType.equals(Void.TYPE)) {
-                    dest = res;
-                } else {
-                    dest = params[1];
-                }
-
-                if (m_check != null) {
-                    failure = (boolean)m_check.invoke(null,  new Object[] { src, dest });
-                } else {
-                    if (isIntArray) {
-                        int[] int_res = (int[])src;
-                        int[] int_dest = (int[])dest;
-                        for (int j = 0; j < int_res.length; j++) {
-                            if (int_res[j] != int_dest[j]) {
-                                System.out.println("Test " + name + " failed for " + j + " src[" + j +"]=" + int_res[j] + ", dest[" + j + "]=" + int_dest[j]);
-                                failure = true;
-                            }
-                        }
-                    } else {
-                        Object[] object_res = (Object[])src;
-                        Object[] object_dest = (Object[])dest;
-                        for (int j = 0; j < object_res.length; j++) {
-                            if (object_res[j] != object_dest[j]) {
-                                System.out.println("Test " + name + " failed for " + j + " src[" + j +"]=" + object_res[j] + ", dest[" + j + "]=" + object_dest[j]);
-                                failure = true;
-                            }
-                        }
-                    }
-                }
-            }
-
-            if (failure) {
-                success = false;
-                break;
-            }
-        }
-    }
-
     public static void main(String[] args) throws Exception {
-        for (int i = 0; i < small_a_src.length; i++) {
-            small_a_src[i] = new A();
-        }
-
-        for (int i = 0; i < small_int_src.length; i++) {
-            small_int_src[i] = i;
-        }
-
-        for (int i = 0; i < large_int_src.length; i++) {
-            large_int_src[i] = i;
-        }
-
-        for (int i = 0; i < 5; i++) {
-            small_object_src[i] = new Object();
-        }
-
         TestArrayCopyAsLoadsStores test = new TestArrayCopyAsLoadsStores();
 
         test.doTest("m1");
--- a/hotspot/test/compiler/arraycopy/TestArrayCopyNoInitDeopt.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/arraycopy/TestArrayCopyNoInitDeopt.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  * @build TestArrayCopyNoInitDeopt
  * @run main ClassFileInstaller sun.hotspot.WhiteBox
- * @run main ClassFileInstaller com.oracle.java.testlibrary.Platform
+ * @run main ClassFileInstaller jdk.test.lib.Platform
  * @run main/othervm -Xmixed -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI
  *                   -XX:-BackgroundCompilation -XX:-UseOnStackReplacement -XX:TypeProfileLevel=020
  *                   TestArrayCopyNoInitDeopt
@@ -40,7 +40,7 @@
 
 import sun.hotspot.WhiteBox;
 import sun.hotspot.code.NMethod;
-import com.oracle.java.testlibrary.Platform;
+import jdk.test.lib.Platform;
 import java.lang.reflect.*;
 
 public class TestArrayCopyNoInitDeopt {
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/compiler/arraycopy/TestArrayCopyUtils.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,223 @@
+/*
+ * 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.lang.annotation.*;
+import java.lang.reflect.*;
+import java.util.*;
+
+abstract class TestArrayCopyUtils {
+    public enum ArraySrc {
+        SMALL,
+        LARGE,
+        ZERO
+    }
+
+    public enum ArrayDst {
+        NONE,
+        NEW,
+        SRC
+    }
+
+    static class A {
+    }
+
+    static class B extends A {
+    }
+
+    static final A[] small_a_src = new A[5];
+    static final A[] large_a_src = new A[10];
+    static final A[] zero_a_src = new A[0];
+    static final int[] small_int_src = new int[5];
+    static final int[] large_int_src = new int[10];
+    static final int[] zero_int_src = new int[0];
+    static final Object[] small_object_src = new Object[5];
+    static Object src;
+
+    @Retention(RetentionPolicy.RUNTIME)
+    @interface Args {
+        ArraySrc src();
+        ArrayDst dst() default ArrayDst.NONE;
+        int[] extra_args() default {};
+    }
+
+    final HashMap<String,Method> tests = new HashMap<>();
+    {
+        for (Method m : this.getClass().getDeclaredMethods()) {
+            if (m.getName().matches("m[0-9]+(_check)?")) {
+                assert(Modifier.isStatic(m.getModifiers())) : m;
+                tests.put(m.getName(), m);
+            }
+        }
+    }
+
+    boolean success = true;
+
+    void doTest(String name) throws Exception {
+        Method m = tests.get(name);
+        Method m_check = tests.get(name + "_check");
+        Class[] paramTypes = m.getParameterTypes();
+        Object[] params = new Object[paramTypes.length];
+        Class retType = m.getReturnType();
+        boolean isIntArray = (retType.isPrimitive() && !retType.equals(Void.TYPE)) ||
+            (retType.equals(Void.TYPE) && paramTypes[0].getComponentType().isPrimitive()) ||
+            (retType.isArray() && retType.getComponentType().isPrimitive());
+
+        Args args = m.getAnnotation(Args.class);
+
+        Object src = null;
+        switch(args.src()) {
+        case SMALL: {
+            if (isIntArray) {
+                src = small_int_src;
+            } else {
+                src = small_a_src;
+            }
+            break;
+        }
+        case LARGE: {
+            if (isIntArray) {
+                src = large_int_src;
+            } else {
+                src = large_a_src;
+            }
+            break;
+        }
+        case ZERO: {
+            if (isIntArray) {
+                src = zero_int_src;
+            } else {
+                src = zero_a_src;
+            }
+            break;
+        }
+        }
+
+        for (int i = 0; i < 20000; i++) {
+            boolean failure = false;
+
+            int p = 0;
+
+            if (params.length > 0) {
+                if (isIntArray) {
+                    params[0] = ((int[])src).clone();
+                } else {
+                    params[0] = ((A[])src).clone();
+                }
+                p++;
+            }
+
+            if (params.length > 1) {
+                switch(args.dst()) {
+                case NEW: {
+                    if (isIntArray) {
+                        params[1] = new int[((int[])params[0]).length];
+                    } else {
+                        params[1] = new A[((A[])params[0]).length];
+                    }
+                    p++;
+                    break;
+                }
+                case SRC: {
+                    params[1] = params[0];
+                    p++;
+                    break;
+                }
+                case NONE: break;
+                }
+            }
+
+            for (int j = 0; j < args.extra_args().length; j++) {
+                params[p+j] = args.extra_args()[j];
+            }
+
+            Object res = m.invoke(null, params);
+
+            if (retType.isPrimitive() && !retType.equals(Void.TYPE)) {
+                int s = (int)res;
+                int sum = 0;
+                int[] int_res = (int[])src;
+                for (int j = 0; j < int_res.length; j++) {
+                    sum += int_res[j];
+                }
+                failure = (s != sum);
+                if (failure) {
+                    System.out.println("Test " + name + " failed: result = " + s + " != " + sum);
+                }
+            } else {
+                Object dest = null;
+                if (!retType.equals(Void.TYPE)) {
+                    dest = res;
+                } else {
+                    dest = params[1];
+                }
+
+                if (m_check != null) {
+                    failure = (boolean)m_check.invoke(null,  new Object[] { src, dest });
+                } else {
+                    if (isIntArray) {
+                        int[] int_res = (int[])src;
+                        int[] int_dest = (int[])dest;
+                        for (int j = 0; j < int_res.length; j++) {
+                            if (int_res[j] != int_dest[j]) {
+                                System.out.println("Test " + name + " failed for " + j + " src[" + j +"]=" + int_res[j] + ", dest[" + j + "]=" + int_dest[j]);
+                                failure = true;
+                            }
+                        }
+                    } else {
+                        Object[] object_res = (Object[])src;
+                        Object[] object_dest = (Object[])dest;
+                        for (int j = 0; j < object_res.length; j++) {
+                            if (object_res[j] != object_dest[j]) {
+                                System.out.println("Test " + name + " failed for " + j + " src[" + j +"]=" + object_res[j] + ", dest[" + j + "]=" + object_dest[j]);
+                                failure = true;
+                            }
+                        }
+                    }
+                }
+            }
+
+            if (failure) {
+                success = false;
+                break;
+            }
+        }
+    }
+
+    TestArrayCopyUtils() {
+        for (int i = 0; i < small_a_src.length; i++) {
+            small_a_src[i] = new A();
+        }
+
+        for (int i = 0; i < small_int_src.length; i++) {
+            small_int_src[i] = i;
+        }
+
+        for (int i = 0; i < large_int_src.length; i++) {
+            large_int_src[i] = i;
+        }
+
+        for (int i = 0; i < 5; i++) {
+            small_object_src[i] = new Object();
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/compiler/arraycopy/TestEliminateArrayCopy.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,195 @@
+/*
+ * 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 8076188
+ * @summary arraycopy to non escaping destination may be eliminated
+ * @compile TestEliminateArrayCopy.java TestArrayCopyUtils.java
+ * @run main/othervm -ea -XX:-BackgroundCompilation -XX:-UseOnStackReplacement -XX:CompileCommand=dontinline,TestEliminateArrayCopy*::m* TestEliminateArrayCopy
+ *
+ */
+
+public class TestEliminateArrayCopy {
+
+    static class CloneTests extends TestInstanceCloneUtils {
+        // object allocation and ArrayCopyNode should be eliminated
+        static void m1(E src) throws CloneNotSupportedException {
+            src.clone();
+        }
+
+        // both object allocations and ArrayCopyNode should be eliminated
+        static void m2(Object dummy) throws CloneNotSupportedException {
+            E src = new E(false);
+            src.clone();
+        }
+
+        // object allocation and ArrayCopyNode should be eliminated. Fields should be loaded from src.
+        static int m3(E src) throws CloneNotSupportedException {
+            E dest = (E)src.clone();
+            return dest.i1 + dest.i2 + dest.i3 + dest.i4 + dest.i5 +
+                dest.i6 + dest.i7 + dest.i8 + dest.i9;
+        }
+    }
+
+    static class ArrayCopyTests extends TestArrayCopyUtils {
+
+        // object allocation and ArrayCopyNode should be eliminated.
+        @Args(src=ArraySrc.LARGE)
+        static int m1() throws CloneNotSupportedException {
+            int[] array_clone = (int[])large_int_src.clone();
+            return array_clone[0] + array_clone[1] + array_clone[2] +
+                array_clone[3] + array_clone[4] + array_clone[5] +
+                array_clone[6] + array_clone[7] + array_clone[8] +
+                array_clone[9];
+        }
+
+        // object allocation and ArrayCopyNode should be eliminated.
+        @Args(src=ArraySrc.LARGE)
+        static int m2() {
+            int[] dest = new int[10];
+            System.arraycopy(large_int_src, 0, dest, 0, 10);
+            return dest[0] + dest[1] + dest[2] + dest[3] + dest[4] +
+                dest[5] + dest[6] + dest[7] + dest[8] + dest[9];
+        }
+
+        // object allocations and ArrayCopyNodes should be eliminated.
+        @Args(src=ArraySrc.LARGE)
+        static int m3() {
+            int[] dest1 = new int[10];
+            System.arraycopy(large_int_src, 0, dest1, 0, 10);
+
+            int[] dest2 = new int[10];
+            System.arraycopy(dest1, 0, dest2, 0, 10);
+
+            return dest2[0] + dest2[1] + dest2[2] + dest2[3] + dest2[4] +
+                dest2[5] + dest2[6] + dest2[7] + dest2[8] + dest2[9];
+        }
+
+        static class m4_class {
+            Object f;
+        }
+
+        static void m4_helper() {}
+
+        // allocations eliminated and arraycopy optimized out
+        @Args(src=ArraySrc.LARGE)
+        static int m4() {
+            int[] dest = new int[10];
+            m4_class o = new m4_class();
+            o.f = dest;
+            m4_helper();
+            System.arraycopy(large_int_src, 0, o.f, 0, 10);
+            return dest[0] + dest[1] + dest[2] + dest[3] + dest[4] +
+                dest[5] + dest[6] + dest[7] + dest[8] + dest[9];
+        }
+
+        static void m5_helper() {}
+
+        // Small copy cannot be converted to loads/stores because
+        // allocation is not close enough to arraycopy but arraycopy
+        // itself can be eliminated
+        @Args(src=ArraySrc.SMALL, dst=ArrayDst.NEW)
+        static void m5(A[] src, A[] dest) {
+            A[] temp = new A[5];
+            m5_helper();
+            System.arraycopy(src, 0, temp, 0, 5);
+            dest[0] = temp[0];
+            dest[1] = temp[1];
+            dest[2] = temp[2];
+            dest[3] = temp[3];
+            dest[4] = temp[4];
+        }
+
+        // object allocation and ArrayCopyNode should be eliminated.
+        @Args(src=ArraySrc.LARGE)
+        static int m6(int [] src) {
+            int res = src[0] + src[1] + src[2] + src[3] + src[4] +
+                src[5] + src[6] + src[7] + src[8] + src[9];
+
+            int[] dest = new int[10];
+
+            System.arraycopy(src, 0, dest, 0, 10);
+
+            res += dest[0] + dest[1] + dest[2] + dest[3] + dest[4] +
+                dest[5] + dest[6] + dest[7] + dest[8] + dest[9];
+            return res/2;
+        }
+
+        @Args(src=ArraySrc.LARGE)
+        static int m7() {
+            int[] dest = new int[10];
+            dest[0] = large_int_src[8];
+            dest[1] = large_int_src[9];
+            System.arraycopy(large_int_src, 0, dest, 2, 8);
+            return dest[0] + dest[1] + dest[2] + dest[3] + dest[4] +
+                dest[5] + dest[6] + dest[7] + dest[8] + dest[9];
+        }
+    }
+
+    // test that OptimizePtrCompare still works
+    static final Object[] m1_array = new Object[10];
+    static boolean m1_array_null_element = false;
+    static void m1(int i) {
+        Object[] array_clone = (Object[])m1_array.clone();
+        if (array_clone[i] == null) {
+            m1_array_null_element = true;
+        }
+    }
+
+    static public void main(String[] args) throws Exception {
+        CloneTests clone_tests = new CloneTests();
+
+        clone_tests.doTest(clone_tests.e, "m1");
+        clone_tests.doTest(null, "m2");
+        clone_tests.doTest(clone_tests.e, "m3");
+
+        ArrayCopyTests ac_tests = new ArrayCopyTests();
+
+        ac_tests.doTest("m1");
+        ac_tests.doTest("m2");
+        ac_tests.doTest("m3");
+        ac_tests.doTest("m4");
+        ac_tests.doTest("m5");
+        ac_tests.doTest("m6");
+        ac_tests.doTest("m7");
+
+        if (!clone_tests.success || !ac_tests.success) {
+            throw new RuntimeException("some tests failed");
+        }
+
+        // Make sure both branches of the if in m1() appear taken
+        for (int i = 0; i < 7000; i++) {
+            m1(0);
+        }
+        m1_array[0] = new Object();
+        for (int i = 0; i < 20000; i++) {
+            m1(0);
+        }
+        m1_array_null_element = false;
+        m1(0);
+        if (m1_array_null_element) {
+            throw new RuntimeException("OptimizePtrCompare test failed");
+        }
+    }
+}
--- a/hotspot/test/compiler/arraycopy/TestInstanceCloneAsLoadsStores.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/arraycopy/TestInstanceCloneAsLoadsStores.java	Wed Jul 05 20:35:10 2017 +0200
@@ -25,200 +25,13 @@
  * @test
  * @bug 6700100
  * @summary small instance clone as loads/stores
+ * @compile TestInstanceCloneAsLoadsStores.java TestInstanceCloneUtils.java
  * @run main/othervm -XX:-BackgroundCompilation -XX:-UseOnStackReplacement -XX:CompileCommand=dontinline,TestInstanceCloneAsLoadsStores::m* TestInstanceCloneAsLoadsStores
  * @run main/othervm -XX:-BackgroundCompilation -XX:-UseOnStackReplacement -XX:CompileCommand=dontinline,TestInstanceCloneAsLoadsStores::m* -XX:+IgnoreUnrecognizedVMOptions -XX:+StressArrayCopyMacroNode TestInstanceCloneAsLoadsStores
  *
  */
 
-import java.lang.reflect.*;
-import java.util.*;
-
-public class TestInstanceCloneAsLoadsStores {
-    static class Base implements Cloneable {
-        void initialize(Class c, int i) {
-            for (Field f : c.getDeclaredFields()) {
-                setVal(f, i);
-                i++;
-            }
-            if (c != Base.class) {
-                initialize(c.getSuperclass(), i);
-            }
-        }
-
-        Base() {
-            initialize(getClass(), 0);
-        }
-
-        void setVal(Field f, int i) {
-            try {
-                if (f.getType() == int.class) {
-                    f.setInt(this, i);
-                    return;
-                } else if (f.getType() == short.class) {
-                    f.setShort(this, (short)i);
-                    return;
-                } else if (f.getType() == byte.class) {
-                    f.setByte(this, (byte)i);
-                    return;
-                } else if (f.getType() == long.class) {
-                    f.setLong(this, i);
-                    return;
-                }
-            } catch(IllegalAccessException iae) {
-                throw new RuntimeException("Getting fields failed");
-            }
-            throw new RuntimeException("unexpected field type");
-        }
-
-        int getVal(Field f) {
-            try {
-                if (f.getType() == int.class) {
-                    return f.getInt(this);
-                } else if (f.getType() == short.class) {
-                    return (int)f.getShort(this);
-                } else if (f.getType() == byte.class) {
-                    return (int)f.getByte(this);
-                } else if (f.getType() == long.class) {
-                    return (int)f.getLong(this);
-                }
-            } catch(IllegalAccessException iae) {
-                throw new RuntimeException("Setting fields failed");
-            }
-            throw new RuntimeException("unexpected field type");
-        }
-
-        boolean fields_equal(Class c, Base o) {
-            for (Field f : c.getDeclaredFields()) {
-                if (getVal(f) != o.getVal(f)) {
-                    return false;
-                }
-            }
-            if (c != Base.class) {
-                return fields_equal(c.getSuperclass(), o);
-            }
-            return true;
-        }
-
-        public boolean equals(Object obj) {
-            return fields_equal(getClass(), (Base)obj);
-        }
-
-        String print_fields(Class c, String s) {
-            for (Field f : c.getDeclaredFields()) {
-                if (s != "") {
-                    s += "\n";
-                }
-                s = s + f + " = " + getVal(f);
-            }
-            if (c != Base.class) {
-                return print_fields(c.getSuperclass(), s);
-            }
-            return s;
-        }
-
-        public String toString() {
-            return print_fields(getClass(), "");
-        }
-
-        int fields_sum(Class c, int s) {
-            for (Field f : c.getDeclaredFields()) {
-                s += getVal(f);
-            }
-            if (c != Base.class) {
-                return fields_sum(c.getSuperclass(), s);
-            }
-            return s;
-        }
-
-        public int sum() {
-            return fields_sum(getClass(), 0);
-        }
-
-    }
-
-    static class A extends Base {
-        int i1;
-        int i2;
-        int i3;
-        int i4;
-        int i5;
-
-        public Object clone() throws CloneNotSupportedException {
-            return super.clone();
-        }
-    }
-
-    static class B extends A {
-        int i6;
-    }
-
-    static final class D extends Base {
-        byte  i1;
-        short i2;
-        long  i3;
-        int   i4;
-        int   i5;
-
-        public Object clone() throws CloneNotSupportedException {
-            return super.clone();
-        }
-    }
-
-    static final class E extends Base {
-        int i1;
-        int i2;
-        int i3;
-        int i4;
-        int i5;
-        int i6;
-        int i7;
-        int i8;
-        int i9;
-
-        public Object clone() throws CloneNotSupportedException {
-            return super.clone();
-        }
-    }
-
-    static final class F extends Base {
-        public Object clone() throws CloneNotSupportedException {
-            return super.clone();
-        }
-    }
-
-    static class G extends Base {
-        int i1;
-        int i2;
-        int i3;
-
-        public Object myclone() throws CloneNotSupportedException {
-            return clone();
-        }
-    }
-
-    static class H extends G {
-        int i4;
-        int i5;
-
-        public Object clone() throws CloneNotSupportedException {
-            return super.clone();
-        }
-    }
-
-    static class J extends Base  {
-        int i1;
-        int i2;
-        int i3;
-
-        public Object myclone() throws CloneNotSupportedException {
-            return clone();
-        }
-    }
-
-    static class K extends J {
-        int i4;
-        int i5;
-    }
+public class TestInstanceCloneAsLoadsStores extends TestInstanceCloneUtils {
 
     // Should be compiled as loads/stores
     static Object m1(D src) throws CloneNotSupportedException {
@@ -269,62 +82,10 @@
         return (J)src.myclone();
     }
 
-    final HashMap<String,Method> tests = new HashMap<>();
-    {
-        for (Method m : this.getClass().getDeclaredMethods()) {
-            if (m.getName().matches("m[0-9]+")) {
-                assert(Modifier.isStatic(m.getModifiers())) : m;
-                tests.put(m.getName(), m);
-            }
-        }
-    }
-
-    boolean success = true;
-
-    void doTest(Base src, String name) throws Exception {
-        Method m = tests.get(name);
-
-        for (int i = 0; i < 20000; i++) {
-            boolean failure = false;
-            Base res = null;
-            int s = 0;
-            if (m.getReturnType().isPrimitive()) {
-                s = (int)m.invoke(null, src);
-                failure = (s != src.sum());
-            } else {
-                res = (Base)m.invoke(null, src);
-                failure = !res.equals(src);
-            }
-            if (failure) {
-                System.out.println("Test " + name + " failed");
-                System.out.println("source: ");
-                System.out.println(src);
-                System.out.println("result: ");
-                if (m.getReturnType().isPrimitive()) {
-                    System.out.println(s);
-                } else {
-                    System.out.println(res);
-                }
-                success = false;
-                break;
-            }
-        }
-    }
-
     public static void main(String[] args) throws Exception {
 
         TestInstanceCloneAsLoadsStores test = new TestInstanceCloneAsLoadsStores();
 
-        A a = new A();
-        B b = new B();
-        D d = new D();
-        E e = new E();
-        F f = new F();
-        G g = new G();
-        H h = new H();
-        J j = new J();
-        K k = new K();
-
         test.doTest(d, "m1");
         test.doTest(d, "m2");
         test.doTest(e, "m3");
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/compiler/arraycopy/TestInstanceCloneUtils.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,310 @@
+/*
+ * 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.lang.reflect.*;
+import java.util.*;
+
+abstract class TestInstanceCloneUtils {
+    static class Base implements Cloneable {
+        void initialize(Class c, int i) {
+            for (Field f : c.getDeclaredFields()) {
+                setVal(f, i);
+                i++;
+            }
+            if (c != Base.class) {
+                initialize(c.getSuperclass(), i);
+            }
+        }
+
+        Base(boolean initialize) {
+            if (initialize) {
+                initialize(getClass(), 0);
+            }
+        }
+
+        void setVal(Field f, int i) {
+            try {
+                if (f.getType() == int.class) {
+                    f.setInt(this, i);
+                    return;
+                } else if (f.getType() == short.class) {
+                    f.setShort(this, (short)i);
+                    return;
+                } else if (f.getType() == byte.class) {
+                    f.setByte(this, (byte)i);
+                    return;
+                } else if (f.getType() == long.class) {
+                    f.setLong(this, i);
+                    return;
+                }
+            } catch(IllegalAccessException iae) {
+                throw new RuntimeException("Getting fields failed");
+            }
+            throw new RuntimeException("unexpected field type");
+        }
+
+        int getVal(Field f) {
+            try {
+                if (f.getType() == int.class) {
+                    return f.getInt(this);
+                } else if (f.getType() == short.class) {
+                    return (int)f.getShort(this);
+                } else if (f.getType() == byte.class) {
+                    return (int)f.getByte(this);
+                } else if (f.getType() == long.class) {
+                    return (int)f.getLong(this);
+                }
+            } catch(IllegalAccessException iae) {
+                throw new RuntimeException("Setting fields failed");
+            }
+            throw new RuntimeException("unexpected field type");
+        }
+
+        boolean fields_equal(Class c, Base o) {
+            for (Field f : c.getDeclaredFields()) {
+                if (getVal(f) != o.getVal(f)) {
+                    return false;
+                }
+            }
+            if (c != Base.class) {
+                return fields_equal(c.getSuperclass(), o);
+            }
+            return true;
+        }
+
+        public boolean equals(Object obj) {
+            return fields_equal(getClass(), (Base)obj);
+        }
+
+        String print_fields(Class c, String s) {
+            for (Field f : c.getDeclaredFields()) {
+                if (s != "") {
+                    s += "\n";
+                }
+                s = s + f + " = " + getVal(f);
+            }
+            if (c != Base.class) {
+                return print_fields(c.getSuperclass(), s);
+            }
+            return s;
+        }
+
+        public String toString() {
+            return print_fields(getClass(), "");
+        }
+
+        int fields_sum(Class c, int s) {
+            for (Field f : c.getDeclaredFields()) {
+                s += getVal(f);
+            }
+            if (c != Base.class) {
+                return fields_sum(c.getSuperclass(), s);
+            }
+            return s;
+        }
+
+        public int sum() {
+            return fields_sum(getClass(), 0);
+        }
+
+    }
+
+    static class A extends Base {
+        int i1;
+        int i2;
+        int i3;
+        int i4;
+        int i5;
+
+        A(boolean initialize) {
+            super(initialize);
+        }
+
+        public Object clone() throws CloneNotSupportedException {
+            return super.clone();
+        }
+    }
+
+    static class B extends A {
+        int i6;
+
+        B(boolean initialize) {
+            super(initialize);
+        }
+    }
+
+    static final class D extends Base {
+        byte  i1;
+        short i2;
+        long  i3;
+        int   i4;
+        int   i5;
+
+        D(boolean initialize) {
+            super(initialize);
+        }
+
+        public Object clone() throws CloneNotSupportedException {
+            return super.clone();
+        }
+    }
+
+    static final class E extends Base {
+        int i1;
+        int i2;
+        int i3;
+        int i4;
+        int i5;
+        int i6;
+        int i7;
+        int i8;
+        int i9;
+
+        E(boolean initialize) {
+            super(initialize);
+        }
+
+        public Object clone() throws CloneNotSupportedException {
+            return super.clone();
+        }
+    }
+
+    static final class F extends Base {
+        F(boolean initialize) {
+            super(initialize);
+        }
+
+        public Object clone() throws CloneNotSupportedException {
+            return super.clone();
+        }
+    }
+
+    static class G extends Base {
+        int i1;
+        int i2;
+        int i3;
+
+        G(boolean initialize) {
+            super(initialize);
+        }
+
+        public Object myclone() throws CloneNotSupportedException {
+            return clone();
+        }
+    }
+
+    static class H extends G {
+        int i4;
+        int i5;
+
+        H(boolean initialize) {
+            super(initialize);
+        }
+
+        public Object clone() throws CloneNotSupportedException {
+            return super.clone();
+        }
+    }
+
+    static class J extends Base  {
+        int i1;
+        int i2;
+        int i3;
+
+        J(boolean initialize) {
+            super(initialize);
+        }
+
+        public Object myclone() throws CloneNotSupportedException {
+            return clone();
+        }
+    }
+
+    static class K extends J {
+        int i4;
+        int i5;
+
+        K(boolean initialize) {
+            super(initialize);
+        }
+
+    }
+
+    static final A a = new A(true);
+    static final B b = new B(true);
+    static final D d = new D(true);
+    static final E e = new E(true);
+    static final F f = new F(true);
+    static final G g = new G(true);
+    static final H h = new H(true);
+    static final J j = new J(true);
+    static final K k = new K(true);
+
+    final HashMap<String,Method> tests = new HashMap<>();
+    {
+        for (Method m : this.getClass().getDeclaredMethods()) {
+            if (m.getName().matches("m[0-9]+")) {
+                assert(Modifier.isStatic(m.getModifiers())) : m;
+                tests.put(m.getName(), m);
+            }
+        }
+    }
+
+    boolean success = true;
+
+    void doTest(Base src, String name) throws Exception {
+        Method m = tests.get(name);
+
+        for (int i = 0; i < 20000; i++) {
+            boolean failure = false;
+            Base res = null;
+            int s = 0;
+            Class retType = m.getReturnType();
+            if (retType.isPrimitive()) {
+                if (!retType.equals(Void.TYPE)) {
+                    s = (int)m.invoke(null, src);
+                    failure = (s != src.sum());
+                } else {
+                    m.invoke(null, src);
+                }
+            } else {
+                res = (Base)m.invoke(null, src);
+                failure = !res.equals(src);
+            }
+            if (failure) {
+                System.out.println("Test " + name + " failed");
+                System.out.println("source: ");
+                System.out.println(src);
+                System.out.println("result: ");
+                if (m.getReturnType().isPrimitive()) {
+                    System.out.println(s);
+                } else {
+                    System.out.println(res);
+                }
+                success = false;
+                break;
+            }
+        }
+    }
+
+}
--- a/hotspot/test/compiler/c2/6589834/Test_ia32.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/c2/6589834/Test_ia32.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build ClassFileInstaller sun.hotspot.WhiteBox com.oracle.java.testlibrary.*
+ * @build ClassFileInstaller sun.hotspot.WhiteBox jdk.test.lib.*
  *        Test_ia32 InlinedArrayCloneTestCase
  * @run main ClassFileInstaller sun.hotspot.WhiteBox
  *                              sun.hotspot.WhiteBox$WhiteBoxPermission
@@ -44,7 +44,7 @@
 
 import java.lang.reflect.Method;
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 import sun.hotspot.WhiteBox;
 
 public class Test_ia32 {
--- a/hotspot/test/compiler/c2/6857159/Test6857159.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/c2/6857159/Test6857159.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class Test6857159 {
     public static void main(String[] args) throws Exception {
--- a/hotspot/test/compiler/c2/7068051/Test7068051.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/c2/7068051/Test7068051.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,8 +33,8 @@
  * @run main/othervm -showversion -Xbatch Test7068051
  */
 
-import com.oracle.java.testlibrary.JDKToolLauncher;
-import com.oracle.java.testlibrary.OutputAnalyzer;
+import jdk.test.lib.JDKToolLauncher;
+import jdk.test.lib.OutputAnalyzer;
 
 import java.io.IOException;
 import java.io.InputStream;
--- a/hotspot/test/compiler/c2/7177917/Test7177917.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/c2/7177917/Test7177917.java	Wed Jul 05 20:35:10 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
@@ -26,7 +26,7 @@
  * Micro-benchmark for Math.pow() and Math.exp()
  */
 
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Utils;
 import java.util.Random;
 
 public class Test7177917 {
--- a/hotspot/test/compiler/c2/8005956/PolynomialRoot.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/c2/8005956/PolynomialRoot.java	Wed Jul 05 20:35:10 2017 +0200
@@ -19,7 +19,7 @@
 * @run main/timeout=300 PolynomialRoot
 */
 
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Utils;
 import java.util.Arrays;
 import java.util.Random;
 
--- a/hotspot/test/compiler/codecache/CheckReservedInitialCodeCacheSizeArgOrder.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/CheckReservedInitialCodeCacheSizeArgOrder.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  * @modules java.base/sun.misc
  *          java.management
  */
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class CheckReservedInitialCodeCacheSizeArgOrder {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/compiler/codecache/CheckSegmentedCodeCache.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/CheckSegmentedCodeCache.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.hotspot.WhiteBox;
 
 /*
--- a/hotspot/test/compiler/codecache/CheckUpperLimit.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/CheckUpperLimit.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  * @modules java.base/sun.misc
  *          java.management
  */
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class CheckUpperLimit {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/compiler/codecache/OverflowCodeCacheTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/OverflowCodeCacheTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,7 +29,7 @@
 import sun.hotspot.WhiteBox;
 import sun.hotspot.code.BlobType;
 import sun.hotspot.code.CodeBlob;
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 
 /*
  * @test OverflowCodeCacheTest
--- a/hotspot/test/compiler/codecache/cli/TestSegmentedCodeCacheOption.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/cli/TestSegmentedCodeCacheOption.java	Wed Jul 05 20:35:10 2017 +0200
@@ -20,9 +20,9 @@
  * or visit www.oracle.com if you need additional information or have any
  * questions.
  */
-import com.oracle.java.testlibrary.ExitCode;
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
+import jdk.test.lib.ExitCode;
+import jdk.test.lib.Platform;
+import jdk.test.lib.cli.CommandLineOptionTest;
 import common.CodeCacheOptions;
 import sun.hotspot.code.BlobType;
 
@@ -35,7 +35,7 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build TestSegmentedCodeCacheOption com.oracle.java.testlibrary.*
+ * @build TestSegmentedCodeCacheOption jdk.test.lib.*
  * @run main TestSegmentedCodeCacheOption
  */
 public class TestSegmentedCodeCacheOption {
--- a/hotspot/test/compiler/codecache/cli/codeheapsize/CodeCacheFreeSpaceRunner.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/cli/codeheapsize/CodeCacheFreeSpaceRunner.java	Wed Jul 05 20:35:10 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
@@ -22,9 +22,9 @@
  */
 package codeheapsize;
 
-import com.oracle.java.testlibrary.ExitCode;
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
+import jdk.test.lib.ExitCode;
+import jdk.test.lib.Platform;
+import jdk.test.lib.cli.CommandLineOptionTest;
 import common.CodeCacheCLITestCase;
 import common.CodeCacheOptions;
 import sun.hotspot.code.BlobType;
--- a/hotspot/test/compiler/codecache/cli/codeheapsize/GenericCodeHeapSizeRunner.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/cli/codeheapsize/GenericCodeHeapSizeRunner.java	Wed Jul 05 20:35:10 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
@@ -22,7 +22,7 @@
  */
 package codeheapsize;
 
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.CommandLineOptionTest;
 import common.CodeCacheCLITestCase;
 import common.CodeCacheOptions;
 import sun.hotspot.code.BlobType;
--- a/hotspot/test/compiler/codecache/cli/codeheapsize/JVMStartupRunner.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/cli/codeheapsize/JVMStartupRunner.java	Wed Jul 05 20:35:10 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
@@ -24,9 +24,9 @@
 
 import common.CodeCacheCLITestCase;
 import common.CodeCacheOptions;
-import com.oracle.java.testlibrary.ExitCode;
-import com.oracle.java.testlibrary.Utils;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
+import jdk.test.lib.ExitCode;
+import jdk.test.lib.Utils;
+import jdk.test.lib.cli.CommandLineOptionTest;
 import sun.hotspot.code.BlobType;
 import java.util.Random;
 
--- a/hotspot/test/compiler/codecache/cli/codeheapsize/TestCodeHeapSizeOptions.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/cli/codeheapsize/TestCodeHeapSizeOptions.java	Wed Jul 05 20:35:10 2017 +0200
@@ -22,7 +22,7 @@
  */
 package codeheapsize;
 
-import com.oracle.java.testlibrary.Platform;
+import jdk.test.lib.Platform;
 import common.CodeCacheCLITestBase;
 import common.CodeCacheCLITestCase;
 import sun.hotspot.code.BlobType;
@@ -36,7 +36,7 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build TestCodeHeapSizeOptions com.oracle.java.testlibrary.* codeheapsize.*
+ * @build TestCodeHeapSizeOptions jdk.test.lib.* codeheapsize.*
  *        common.*
  * @run main/timeout=240 codeheapsize.TestCodeHeapSizeOptions
  */
--- a/hotspot/test/compiler/codecache/cli/common/CodeCacheCLITestCase.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/cli/common/CodeCacheCLITestCase.java	Wed Jul 05 20:35:10 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
@@ -22,8 +22,8 @@
  */
 package common;
 
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
+import jdk.test.lib.Platform;
+import jdk.test.lib.cli.CommandLineOptionTest;
 import sun.hotspot.code.BlobType;
 
 import java.util.Collections;
--- a/hotspot/test/compiler/codecache/cli/common/CodeCacheOptions.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/cli/common/CodeCacheOptions.java	Wed Jul 05 20:35:10 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
@@ -22,7 +22,7 @@
  */
 package common;
 
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.CommandLineOptionTest;
 import sun.hotspot.code.BlobType;
 
 import java.util.ArrayList;
--- a/hotspot/test/compiler/codecache/cli/printcodecache/PrintCodeCacheRunner.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/cli/printcodecache/PrintCodeCacheRunner.java	Wed Jul 05 20:35:10 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
@@ -22,8 +22,8 @@
  */
 package printcodecache;
 
-import com.oracle.java.testlibrary.ExitCode;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
+import jdk.test.lib.ExitCode;
+import jdk.test.lib.cli.CommandLineOptionTest;
 import common.CodeCacheCLITestCase;
 import common.CodeCacheInfoFormatter;
 import common.CodeCacheOptions;
--- a/hotspot/test/compiler/codecache/cli/printcodecache/TestPrintCodeCacheOption.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/cli/printcodecache/TestPrintCodeCacheOption.java	Wed Jul 05 20:35:10 2017 +0200
@@ -35,7 +35,7 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build TestPrintCodeCacheOption com.oracle.java.testlibrary.*
+ * @build TestPrintCodeCacheOption jdk.test.lib.*
  *        printcodecache.* common.*
  * @run main/timeout=240 printcodecache.TestPrintCodeCacheOption
  */
--- a/hotspot/test/compiler/codecache/dtrace/SegmentedCodeCacheDtraceTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/dtrace/SegmentedCodeCacheDtraceTest.java	Wed Jul 05 20:35:10 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
@@ -21,12 +21,12 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.JDKToolFinder;
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.Utils;
-import com.oracle.java.testlibrary.dtrace.DtraceResultsAnalyzer;
-import com.oracle.java.testlibrary.dtrace.DtraceRunner;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.JDKToolFinder;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.Utils;
+import jdk.test.lib.dtrace.DtraceResultsAnalyzer;
+import jdk.test.lib.dtrace.DtraceRunner;
 import java.io.IOException;
 import java.lang.reflect.Executable;
 import java.nio.file.Files;
@@ -115,7 +115,7 @@
 
     public static void main(String args[]) {
         int iterations
-                = Integer.getInteger("com.oracle.java.testlibrary.iterations", 1);
+                = Integer.getInteger("jdk.test.lib.iterations", 1);
         if (!DtraceRunner.dtraceAvailable()) {
             System.out.println("INFO: There is no dtrace avaiable. Skipping.");
             return;
--- a/hotspot/test/compiler/codecache/dtrace/SegmentedCodeCacheDtraceTestWorker.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/dtrace/SegmentedCodeCacheDtraceTestWorker.java	Wed Jul 05 20:35:10 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
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Utils;
 import java.lang.reflect.Executable;
 import java.util.ArrayList;
 import java.util.Arrays;
--- a/hotspot/test/compiler/codecache/jmx/BeanTypeTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/jmx/BeanTypeTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 import java.lang.management.MemoryType;
 import sun.hotspot.code.BlobType;
 
--- a/hotspot/test/compiler/codecache/jmx/CodeCacheUtils.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/jmx/CodeCacheUtils.java	Wed Jul 05 20:35:10 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
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Utils;
 import java.lang.management.MemoryPoolMXBean;
 import javax.management.Notification;
 import sun.hotspot.WhiteBox;
--- a/hotspot/test/compiler/codecache/jmx/CodeHeapBeanPresenceTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/jmx/CodeHeapBeanPresenceTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 import java.util.EnumSet;
 import sun.hotspot.code.BlobType;
 
--- a/hotspot/test/compiler/codecache/jmx/GetUsageTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/jmx/GetUsageTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 import java.lang.management.MemoryPoolMXBean;
 import java.util.HashMap;
 import java.util.Map;
--- a/hotspot/test/compiler/codecache/jmx/InitialAndMaxUsageTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/jmx/InitialAndMaxUsageTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 import java.lang.management.MemoryPoolMXBean;
 import java.util.ArrayList;
 import java.util.List;
--- a/hotspot/test/compiler/codecache/jmx/ManagerNamesTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/jmx/ManagerNamesTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 import java.lang.management.MemoryPoolMXBean;
 import sun.hotspot.code.BlobType;
 
--- a/hotspot/test/compiler/codecache/jmx/MemoryPoolsPresenceTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/jmx/MemoryPoolsPresenceTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 import java.lang.management.ManagementFactory;
 import java.lang.management.MemoryManagerMXBean;
 import java.util.HashMap;
--- a/hotspot/test/compiler/codecache/jmx/PeakUsageTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/jmx/PeakUsageTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 import java.lang.management.MemoryPoolMXBean;
 import sun.hotspot.code.BlobType;
 
--- a/hotspot/test/compiler/codecache/jmx/PoolsIndependenceTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/jmx/PoolsIndependenceTest.java	Wed Jul 05 20:35:10 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
@@ -21,8 +21,8 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.Utils;
 import java.lang.management.ManagementFactory;
 import java.lang.management.MemoryNotificationInfo;
 import java.lang.management.MemoryPoolMXBean;
--- a/hotspot/test/compiler/codecache/jmx/ThresholdNotificationsTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/jmx/ThresholdNotificationsTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,8 +21,8 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.Utils;
 import java.lang.management.ManagementFactory;
 import java.lang.management.MemoryNotificationInfo;
 import java.lang.management.MemoryPoolMXBean;
@@ -83,7 +83,7 @@
 
     protected void runTest() {
         int iterationsCount =
-            Integer.getInteger("com.oracle.java.testlibrary.iterations", 1);
+            Integer.getInteger("jdk.test.lib.iterations", 1);
         MemoryPoolMXBean bean = btype.getMemoryPool();
         ((NotificationEmitter) ManagementFactory.getMemoryMXBean()).
                 addNotificationListener(this, null, null);
--- a/hotspot/test/compiler/codecache/jmx/UsageThresholdExceededSeveralTimesTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/jmx/UsageThresholdExceededSeveralTimesTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  * @run main/othervm -Xbootclasspath/a:. -XX:-UseCodeCacheFlushing
  *     -XX:-MethodFlushing -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI
  *     -XX:+SegmentedCodeCache -XX:CompileCommand=compileonly,null::*
- *     -Dcom.oracle.java.testlibrary.iterations=10 UsageThresholdExceededTest
+ *     -Djdk.test.lib.iterations=10 UsageThresholdExceededTest
  * @summary verifying that getUsageThresholdCount() returns correct value
  *     after threshold has been hit several times
  */
--- a/hotspot/test/compiler/codecache/jmx/UsageThresholdExceededTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/jmx/UsageThresholdExceededTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 import java.lang.management.MemoryPoolMXBean;
 import sun.hotspot.code.BlobType;
 
@@ -52,7 +52,7 @@
 
     public static void main(String[] args) {
         int iterationsCount =
-            Integer.getInteger("com.oracle.java.testlibrary.iterations", 1);
+            Integer.getInteger("jdk.test.lib.iterations", 1);
         for (BlobType btype : BlobType.getAvailable()) {
             if (CodeCacheUtils.isCodeHeapPredictable(btype)) {
                 new UsageThresholdExceededTest(btype, iterationsCount)
--- a/hotspot/test/compiler/codecache/jmx/UsageThresholdIncreasedTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/jmx/UsageThresholdIncreasedTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 import java.lang.management.MemoryPoolMXBean;
 import sun.hotspot.code.BlobType;
 
--- a/hotspot/test/compiler/codecache/jmx/UsageThresholdNotExceededTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/jmx/UsageThresholdNotExceededTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 import java.lang.management.MemoryPoolMXBean;
 import sun.hotspot.code.BlobType;
 
--- a/hotspot/test/compiler/codecache/stress/CodeCacheStressRunner.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/stress/CodeCacheStressRunner.java	Wed Jul 05 20:35:10 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
@@ -22,8 +22,8 @@
  *
  */
 
-import com.oracle.java.testlibrary.TimeLimitedRunner;
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.TimeLimitedRunner;
+import jdk.test.lib.Utils;
 
 public class CodeCacheStressRunner {
     private final Runnable action;
--- a/hotspot/test/compiler/codecache/stress/Helper.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/stress/Helper.java	Wed Jul 05 20:35:10 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
@@ -28,10 +28,10 @@
 import java.util.concurrent.Callable;
 import java.util.Random;
 
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.ByteCodeLoader;
-import com.oracle.java.testlibrary.InfiniteLoop;
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.ByteCodeLoader;
+import jdk.test.lib.InfiniteLoop;
+import jdk.test.lib.Utils;
 import sun.hotspot.WhiteBox;
 
 public final class Helper {
--- a/hotspot/test/compiler/codecache/stress/OverloadCompileQueueTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codecache/stress/OverloadCompileQueueTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -25,7 +25,7 @@
 import java.lang.reflect.Method;
 import java.util.stream.IntStream;
 
-import com.oracle.java.testlibrary.Platform;
+import jdk.test.lib.Platform;
 
 /*
  * @test OverloadCompileQueueTest
--- a/hotspot/test/compiler/codegen/6896617/Test6896617.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codegen/6896617/Test6896617.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
  *
  */
 
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Utils;
 import java.nio.ByteBuffer;
 import java.nio.CharBuffer;
 import java.nio.charset.Charset;
--- a/hotspot/test/compiler/codegen/7100757/Test7100757.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codegen/7100757/Test7100757.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  * @run main/timeout=300 Test7100757
  */
 
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Utils;
 import java.util.BitSet;
 import java.util.Random;
 
--- a/hotspot/test/compiler/codegen/7184394/TestAESBase.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/codegen/7184394/TestAESBase.java	Wed Jul 05 20:35:10 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
@@ -26,7 +26,7 @@
  * @author Tom Deneau
  */
 
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Utils;
 import java.security.AlgorithmParameters;
 import java.util.Random;
 import javax.crypto.Cipher;
--- a/hotspot/test/compiler/cpuflags/RestoreMXCSR.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/cpuflags/RestoreMXCSR.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,7 +29,7 @@
  * @modules java.base/sun.misc
  *          java.management
  */
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class RestoreMXCSR {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/compiler/debug/VerifyAdapterSharing.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/debug/VerifyAdapterSharing.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,7 +29,7 @@
  * @modules java.base/sun.misc
  *          java.management
  */
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class VerifyAdapterSharing {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/compiler/dependencies/MonomorphicObjectCall/TestMonomorphicObjectCall.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/dependencies/MonomorphicObjectCall/TestMonomorphicObjectCall.java	Wed Jul 05 20:35:10 2017 +0200
@@ -25,7 +25,7 @@
 import java.util.ArrayList;
 import java.util.Collections;
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 /*
  * @test
--- a/hotspot/test/compiler/eliminateAutobox/UnsignedLoads.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/eliminateAutobox/UnsignedLoads.java	Wed Jul 05 20:35:10 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
@@ -30,7 +30,7 @@
  *                   -XX:CompileOnly=::valueOf,::byteValue,::shortValue,::testUnsignedByte,::testUnsignedShort
  *                   UnsignedLoads
  */
-import static com.oracle.java.testlibrary.Asserts.assertEQ;
+import static jdk.test.lib.Asserts.assertEQ;
 
 public class UnsignedLoads {
     public static int testUnsignedByte() {
--- a/hotspot/test/compiler/intrinsics/bmi/BMITestRunner.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/bmi/BMITestRunner.java	Wed Jul 05 20:35:10 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
@@ -22,10 +22,10 @@
  *
  */
 
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
+import jdk.test.lib.Utils;
 import java.io.IOException;
 import java.nio.file.Files;
 import java.nio.file.Paths;
--- a/hotspot/test/compiler/intrinsics/bmi/verifycode/BmiIntrinsicBase.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/bmi/verifycode/BmiIntrinsicBase.java	Wed Jul 05 20:35:10 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
@@ -22,9 +22,9 @@
  *
  */
 
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.Platform;
+import jdk.test.lib.Utils;
 import sun.hotspot.code.NMethod;
 import sun.hotspot.cpuinfo.CPUInfo;
 
--- a/hotspot/test/compiler/intrinsics/classcast/NullCheckDroppingsTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/classcast/NullCheckDroppingsTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -25,13 +25,14 @@
  * @test NullCheckDroppingsTest
  * @bug 8054492
  * @summary "Casting can result in redundant null checks in generated code"
- * @library /testlibrary /../../test/lib /testlibrary/com/oracle/java/testlibrary
+ * @library /testlibrary /../../test/lib
  * @modules java.base/sun.misc
  *          java.management
+ * @build ClassFileInstaller sun.hotspot.WhiteBox jdk.test.lib.*
  * @build NullCheckDroppingsTest
  * @run main ClassFileInstaller sun.hotspot.WhiteBox
  *                              sun.hotspot.WhiteBox$WhiteBoxPermission
- * @run main ClassFileInstaller com.oracle.java.testlibrary.Platform
+ * @run main ClassFileInstaller jdk.test.lib.Platform
  * @run main/othervm -Xbootclasspath/a:. -XX:+IgnoreUnrecognizedVMOptions -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI
  *                   -Xmixed -XX:-BackgroundCompilation -XX:-TieredCompilation -XX:CompileThreshold=1000
  *                   -XX:CompileCommand=exclude,NullCheckDroppingsTest::runTest NullCheckDroppingsTest
@@ -39,7 +40,7 @@
 
 import sun.hotspot.WhiteBox;
 import sun.hotspot.code.NMethod;
-import com.oracle.java.testlibrary.Platform;
+import jdk.test.lib.Platform;
 
 import java.lang.reflect.Method;
 import java.lang.invoke.MethodHandle;
--- a/hotspot/test/compiler/intrinsics/clone/TestObjectClone.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/clone/TestObjectClone.java	Wed Jul 05 20:35:10 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
@@ -29,7 +29,7 @@
  * @library /testlibrary
  * @run main/othervm -XX:-TieredCompilation -Xbatch -XX:CompileOnly=TestObjectClone::f TestObjectClone
  */
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 
 public class TestObjectClone implements Cloneable {
     static class A extends TestObjectClone {}
--- a/hotspot/test/compiler/intrinsics/mathexact/AddExactIRepeatTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/mathexact/AddExactIRepeatTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
  *
  */
 
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Utils;
 import java.util.Random;
 
 public class AddExactIRepeatTest {
--- a/hotspot/test/compiler/intrinsics/mathexact/MulExactIRepeatTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/mathexact/MulExactIRepeatTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
  *
  */
 
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Utils;
 import java.util.Random;
 
 public class MulExactIRepeatTest {
--- a/hotspot/test/compiler/intrinsics/mathexact/SubExactIRepeatTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/mathexact/SubExactIRepeatTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
  *
  */
 
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Utils;
 import java.util.Random;
 
 public class SubExactIRepeatTest {
--- a/hotspot/test/compiler/intrinsics/mathexact/Verify.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/mathexact/Verify.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013, 2014, 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
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Utils;
 import java.util.Random;
 
 /**
--- a/hotspot/test/compiler/intrinsics/mathexact/sanity/IntrinsicBase.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/mathexact/sanity/IntrinsicBase.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013, 2014, 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
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Platform;
+import jdk.test.lib.Platform;
 import intrinsics.Verifier;
 
 import java.io.FileOutputStream;
@@ -145,7 +145,8 @@
 
         @Override
         protected boolean isIntrinsicSupported() {
-            return isServerVM() && Boolean.valueOf(useMathExactIntrinsics) && Platform.isX64();
+            return isServerVM() && Boolean.valueOf(useMathExactIntrinsics) &&
+                (Platform.isX64() || Platform.isPPC());
         }
 
         @Override
--- a/hotspot/test/compiler/intrinsics/sha/cli/SHAOptionsBase.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/sha/cli/SHAOptionsBase.java	Wed Jul 05 20:35:10 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
@@ -21,8 +21,8 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
+import jdk.test.lib.Platform;
+import jdk.test.lib.cli.CommandLineOptionTest;
 import sha.predicate.IntrinsicPredicates;
 
 import java.util.function.BooleanSupplier;
--- a/hotspot/test/compiler/intrinsics/sha/cli/testcases/GenericTestCaseForOtherCPU.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/sha/cli/testcases/GenericTestCaseForOtherCPU.java	Wed Jul 05 20:35:10 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
@@ -21,11 +21,11 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.ExitCode;
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.NotPredicate;
-import com.oracle.java.testlibrary.cli.predicate.OrPredicate;
+import jdk.test.lib.ExitCode;
+import jdk.test.lib.Platform;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.NotPredicate;
+import jdk.test.lib.cli.predicate.OrPredicate;
 
 /**
  * Generic test case for SHA-related options targeted to non-x86 and
--- a/hotspot/test/compiler/intrinsics/sha/cli/testcases/GenericTestCaseForSupportedSparcCPU.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/sha/cli/testcases/GenericTestCaseForSupportedSparcCPU.java	Wed Jul 05 20:35:10 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
@@ -21,10 +21,10 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.ExitCode;
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.ExitCode;
+import jdk.test.lib.Platform;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 
 /**
  * Generic test case for SHA-related options targeted to SPARC CPUs which
--- a/hotspot/test/compiler/intrinsics/sha/cli/testcases/GenericTestCaseForUnsupportedSparcCPU.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/sha/cli/testcases/GenericTestCaseForUnsupportedSparcCPU.java	Wed Jul 05 20:35:10 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
@@ -21,11 +21,11 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.ExitCode;
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
-import com.oracle.java.testlibrary.cli.predicate.NotPredicate;
+import jdk.test.lib.ExitCode;
+import jdk.test.lib.Platform;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
+import jdk.test.lib.cli.predicate.NotPredicate;
 
 /**
  * Generic test case for SHA-related options targeted to SPARC CPUs which don't
--- a/hotspot/test/compiler/intrinsics/sha/cli/testcases/GenericTestCaseForUnsupportedX86CPU.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/sha/cli/testcases/GenericTestCaseForUnsupportedX86CPU.java	Wed Jul 05 20:35:10 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
@@ -21,10 +21,10 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.ExitCode;
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.OrPredicate;
+import jdk.test.lib.ExitCode;
+import jdk.test.lib.Platform;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.OrPredicate;
 
 /**
  * Generic test case for SHA-related options targeted to X86 CPUs that don't
--- a/hotspot/test/compiler/intrinsics/sha/cli/testcases/UseSHAIntrinsicsSpecificTestCaseForUnsupportedSparcCPU.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/sha/cli/testcases/UseSHAIntrinsicsSpecificTestCaseForUnsupportedSparcCPU.java	Wed Jul 05 20:35:10 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
@@ -21,11 +21,11 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.ExitCode;
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
-import com.oracle.java.testlibrary.cli.predicate.NotPredicate;
+import jdk.test.lib.ExitCode;
+import jdk.test.lib.Platform;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
+import jdk.test.lib.cli.predicate.NotPredicate;
 import sha.predicate.IntrinsicPredicates;
 
 /**
--- a/hotspot/test/compiler/intrinsics/sha/cli/testcases/UseSHASpecificTestCaseForSupportedSparcCPU.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/sha/cli/testcases/UseSHASpecificTestCaseForSupportedSparcCPU.java	Wed Jul 05 20:35:10 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
@@ -21,11 +21,11 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.ExitCode;
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.ExitCode;
+import jdk.test.lib.Platform;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import sha.predicate.IntrinsicPredicates;
 
 /**
--- a/hotspot/test/compiler/intrinsics/sha/cli/testcases/UseSHASpecificTestCaseForUnsupportedSparcCPU.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/sha/cli/testcases/UseSHASpecificTestCaseForUnsupportedSparcCPU.java	Wed Jul 05 20:35:10 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
@@ -21,12 +21,12 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.ExitCode;
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
-import com.oracle.java.testlibrary.cli.predicate.NotPredicate;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.ExitCode;
+import jdk.test.lib.Platform;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
+import jdk.test.lib.cli.predicate.NotPredicate;
 import sha.predicate.IntrinsicPredicates;
 
 /**
--- a/hotspot/test/compiler/intrinsics/unsafe/HeapByteBufferTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/intrinsics/unsafe/HeapByteBufferTest.java	Wed Jul 05 20:35:10 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.
 // Copyright (c) 2015, Red Hat Inc. All rights reserved.
 // DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
 //
@@ -23,7 +23,7 @@
 //
 //
 
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Utils;
 import static java.lang.Math.abs;
 import java.nio.ByteBuffer;
 import java.nio.ByteOrder;
--- a/hotspot/test/compiler/jsr292/ConcurrentClassLoadingTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/jsr292/ConcurrentClassLoadingTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  * @run main/othervm ConcurrentClassLoadingTest
  */
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Utils;
 import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.List;
--- a/hotspot/test/compiler/jsr292/MHInlineTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/jsr292/MHInlineTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,8 +29,8 @@
  * @run main/othervm MHInlineTest
  */
 import java.lang.invoke.*;
-import com.oracle.java.testlibrary.*;
-import static com.oracle.java.testlibrary.Asserts.*;
+import jdk.test.lib.*;
+import static jdk.test.lib.Asserts.*;
 
 public class MHInlineTest {
     public static void main(String[] args) throws Exception {
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/compiler/loopopts/superword/ReductionPerf.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,252 @@
+/*
+ * 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 8074981
+ * @summary Add C2 x86 Superword support for scalar product reduction optimizations : int test
+ *
+ * @run main/othervm -XX:+IgnoreUnrecognizedVMOptions -XX:+SuperWordReductions -XX:LoopUnrollLimit=250 -XX:CompileThresholdScaling=0.1 -XX:CompileCommand=exclude,ReductionPerf::main ReductionPerf
+ * @run main/othervm -XX:+IgnoreUnrecognizedVMOptions -XX:-SuperWordReductions -XX:LoopUnrollLimit=250 -XX:CompileThresholdScaling=0.1 -XX:CompileCommand=exclude,ReductionPerf::main ReductionPerf
+ */
+
+public class ReductionPerf {
+  public static void main(String[] args) throws Exception {
+    int[] a1 = new int[8*1024];
+    int[] a2 = new int[8*1024];
+    int[] a3 = new int[8*1024];
+    long[] b1 = new long[8*1024];
+    long[] b2 = new long[8*1024];
+    long[] b3 = new long[8*1024];
+    float[] c1 = new float[8*1024];
+    float[] c2 = new float[8*1024];
+    float[] c3 = new float[8*1024];
+    double[] d1 = new double[8*1024];
+    double[] d2 = new double[8*1024];
+    double[] d3 = new double[8*1024];
+
+    ReductionInit(a1,a2,a3,b1,b2,b3,c1,c2,c3,d1,d2,d3);
+
+    int    sumIv = sumInt(a1,a2,a3);
+    long   sumLv = sumLong(b1,b2,b3);
+    float  sumFv = sumFloat(c1,c2,c3);
+    double sumDv = sumDouble(d1,d2,d3);
+    int    mulIv = prodInt(a1,a2,a3);
+    long   mulLv = prodLong(b1,b2,b3);
+    float  mulFv = prodFloat(c1,c2,c3);
+    double mulDv = prodDouble(d1,d2,d3);
+
+    int    sumI = 0;
+    long   sumL = 0;
+    float  sumF = 0.f;
+    double sumD = 0.;
+    int    mulI = 0;
+    long   mulL = 0;
+    float  mulF = 0.f;
+    double mulD = 0.;
+
+    System.out.println("Warmup ...");
+    long  start = System.currentTimeMillis();
+
+    for(int j = 0; j < 2000; j++) {
+      sumI = sumInt(a1,a2,a3);
+      sumL = sumLong(b1,b2,b3);
+      sumF = sumFloat(c1,c2,c3);
+      sumD = sumDouble(d1,d2,d3);
+      mulI = prodInt(a1,a2,a3);
+      mulL = prodLong(b1,b2,b3);
+      mulF = prodFloat(c1,c2,c3);
+      mulD = prodDouble(d1,d2,d3);
+    }
+
+    long stop = System.currentTimeMillis();
+    System.out.println(" Warmup is done in " + (stop - start) + " msec");
+
+    if (sumIv != sumI) {
+      System.out.println("sum int:    " + sumIv + " != " + sumI);
+    }
+    if (sumLv != sumL) {
+      System.out.println("sum long:   " + sumLv + " != " + sumL);
+    }
+    if (sumFv != sumF) {
+      System.out.println("sum float:  " + sumFv + " != " + sumF);
+    }
+    if (sumDv != sumD) {
+      System.out.println("sum double: " + sumDv + " != " + sumD);
+    }
+    if (mulIv != mulI) {
+      System.out.println("prod int:    " + mulIv + " != " + mulI);
+    }
+    if (mulLv != mulL) {
+      System.out.println("prod long:   " + mulLv + " != " + mulL);
+    }
+    if (mulFv != mulF) {
+      System.out.println("prod float:  " + mulFv + " != " + mulF);
+    }
+    if (mulDv != mulD) {
+      System.out.println("prod double: " + mulDv + " != " + mulD);
+    }
+
+    start = System.currentTimeMillis();
+    for (int j = 0; j < 5000; j++) {
+      sumI = sumInt(a1, a2 ,a3);
+    }
+    stop = System.currentTimeMillis();
+    System.out.println("sum int:    " + (stop - start));
+
+    start = System.currentTimeMillis();
+    for (int j = 0; j < 5000; j++) {
+      sumL = sumLong(b1, b2, b3);
+    }
+    stop = System.currentTimeMillis();
+    System.out.println("sum long:   " + (stop - start));
+
+    start = System.currentTimeMillis();
+    for (int j = 0; j < 5000; j++) {
+      sumF = sumFloat(c1, c2, c3);
+    }
+    stop = System.currentTimeMillis();
+    System.out.println("sum float:  " + (stop - start));
+
+    start = System.currentTimeMillis();
+    for (int j = 0; j < 5000; j++) {
+      sumD = sumDouble(d1, d2, d3);
+    }
+    stop = System.currentTimeMillis();
+    System.out.println("sum double: " + (stop - start));
+
+    start = System.currentTimeMillis();
+    for (int j = 0; j < 5000; j++) {
+      mulI = prodInt(a1, a2, a3);
+    }
+    stop = System.currentTimeMillis();
+    System.out.println("prod int:    " + (stop - start));
+
+    start = System.currentTimeMillis();
+    for (int j = 0; j < 5000; j++) {
+      mulL = prodLong(b1, b2 ,b3);
+    }
+    stop = System.currentTimeMillis();
+    System.out.println("prod long:   " + (stop - start));
+
+    start = System.currentTimeMillis();
+    for (int j = 0; j < 5000; j++) {
+      mulF = prodFloat(c1, c2, c3);
+    }
+    stop = System.currentTimeMillis();
+    System.out.println("prod float:  " + (stop - start));
+
+    start = System.currentTimeMillis();
+    for (int j = 0; j < 5000; j++) {
+      mulD = prodDouble(d1, d2, d3);
+    }
+    stop = System.currentTimeMillis();
+    System.out.println("prod double: " + (stop - start));
+
+  }
+
+  public static void ReductionInit(int[]    a1, int[]    a2, int[]    a3,
+                                   long[]   b1, long[]   b2, long[]   b3,
+                                   float[]  c1, float[]  c2, float[]  c3,
+                                   double[] d1, double[] d2, double[] d3 ) {
+    for(int i = 0; i < a1.length; i++) {
+      a1[i] =          (i + 0);
+      a2[i] =          (i + 1);
+      a3[i] =          (i + 2);
+      b1[i] =   (long) (i + 0);
+      b2[i] =   (long) (i + 1);
+      b3[i] =   (long) (i + 2);
+      c1[i] =  (float) (i + 0);
+      c2[i] =  (float) (i + 1);
+      c3[i] =  (float) (i + 2);
+      d1[i] = (double) (i + 0);
+      d2[i] = (double) (i + 1);
+      d3[i] = (double) (i + 2);
+    }
+  }
+
+  public static int sumInt(int[] a1, int[] a2, int[] a3) {
+    int total = 0;
+    for(int i = 0; i < a1.length; i++) {
+      total += (a1[i] * a2[i]) + (a1[i] * a3[i]) + (a2[i] * a3[i]);
+    }
+    return total;
+  }
+
+  public static long sumLong(long[] b1, long[] b2, long[] b3) {
+    long total = 0;
+    for(int i = 0; i < b1.length; i++) {
+      total += (b1[i] * b2[i]) + (b1[i] * b3[i]) + (b2[i] * b3[i]);
+    }
+    return total;
+  }
+
+  public static float sumFloat(float[] c1, float[] c2, float[] c3) {
+    float total = 0;
+    for(int i = 0; i < c1.length; i++) {
+      total += (c1[i] * c2[i]) + (c1[i] * c3[i]) + (c2[i] * c3[i]);
+    }
+    return total;
+  }
+
+  public static double sumDouble(double[] d1, double[] d2, double[] d3) {
+    double total = 0;
+    for(int i = 0; i < d1.length; i++) {
+      total += (d1[i] * d2[i]) + (d1[i] * d3[i]) + (d2[i] * d3[i]);
+    }
+    return total;
+  }
+
+  public static int prodInt(int[] a1, int[] a2, int[] a3) {
+    int total = 1;
+    for(int i = 0; i < a1.length; i++) {
+      total *= (a1[i] * a2[i]) + (a1[i] * a3[i]) + (a2[i] * a3[i]);
+    }
+    return total;
+  }
+
+  public static long prodLong(long[] b1, long[] b2, long[] b3) {
+    long total = 1;
+    for(int i = 0; i < b1.length; i++) {
+      total *= (b1[i] * b2[i]) + (b1[i] * b3[i]) + (b2[i] * b3[i]);
+    }
+    return total;
+  }
+
+  public static float prodFloat(float[] c1, float[] c2, float[] c3) {
+    float total = 1;
+    for(int i = 0; i < c1.length; i++) {
+      total *= (c1[i] * c2[i]) + (c1[i] * c3[i]) + (c2[i] * c3[i]);
+    }
+    return total;
+  }
+
+  public static double prodDouble(double[] d1, double[] d2, double[] d3) {
+    double total = 1;
+    for(int i = 0; i < d1.length; i++) {
+      total *= (d1[i] * d2[i]) + (d1[i] * d3[i]) + (d2[i] * d3[i]);
+    }
+    return total;
+  }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/compiler/loopopts/superword/SumRed_Long.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,92 @@
+/*
+ * 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 8076276
+ * @summary Add C2 x86 Superword support for scalar sum reduction optimizations : long test
+ *
+ * @run main/othervm -XX:+IgnoreUnrecognizedVMOptions -XX:+SuperWordReductions -XX:LoopUnrollLimit=250 -XX:LoopMaxUnroll=4 -XX:CompileThresholdScaling=0.1 SumRed_Double
+ * @run main/othervm -XX:+IgnoreUnrecognizedVMOptions -XX:-SuperWordReductions -XX:LoopUnrollLimit=250 -XX:LoopMaxUnroll=4 -XX:CompileThresholdScaling=0.1 SumRed_Double
+ *
+ * @run main/othervm -XX:+IgnoreUnrecognizedVMOptions -XX:+SuperWordReductions -XX:LoopUnrollLimit=250 -XX:LoopMaxUnroll=8 -XX:CompileThresholdScaling=0.1 SumRed_Double
+ * @run main/othervm -XX:+IgnoreUnrecognizedVMOptions -XX:-SuperWordReductions -XX:LoopUnrollLimit=250 -XX:LoopMaxUnroll=8 -XX:CompileThresholdScaling=0.1 SumRed_Double
+ *
+ */
+
+public class SumRed_Long
+{
+  public static void main(String[] args) throws Exception {
+    long[] a = new long[256*1024];
+    long[] b = new long[256*1024];
+    long[] c = new long[256*1024];
+    long[] d = new long[256*1024];
+    sumReductionInit(a,b,c);
+    long total = 0;
+    long valid = 262144000;
+    for(int j = 0; j < 2000; j++) {
+      total = sumReductionImplement(a,b,c,d,total);
+    }
+    total = (int)total;
+    if(total == valid) {
+      System.out.println("Success");
+    } else {
+      System.out.println("Invalid sum of elements variable in total: " + total);
+      System.out.println("Expected value = " + valid);
+      throw new Exception("Failed");
+    }
+  }
+
+  public static void sumReductionInit(
+    long[] a,
+    long[] b,
+    long[] c)
+  {
+    for(int j = 0; j < 1; j++)
+    {
+      for(int i = 0; i < a.length; i++)
+      {
+        a[i] = i * 1 + j;
+        b[i] = i * 1 - j;
+        c[i] = i + j;
+      }
+    }
+  }
+
+  public static long sumReductionImplement(
+    long[] a,
+    long[] b,
+    long[] c,
+    long[] d,
+    long total)
+  {
+    for(int i = 0; i < a.length; i++)
+    {
+      d[i]= (a[i] * b[i]) + (a[i] * c[i]) + (b[i] * c[i]);
+      total += d[i];
+    }
+    return total;
+  }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/compiler/loopopts/superword/TestVectorizationWithInvariant.java	Wed Jul 05 20:35:10 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.
+ *
+ */
+
+import jdk.test.lib.*;
+import sun.misc.Unsafe;
+
+/**
+ * @test
+ * @bug 8078497
+ * @summary Tests correct alignment of vectors with loop invariant offset.
+ * @library /testlibrary
+ * @run main TestVectorizationWithInvariant
+ */
+public class TestVectorizationWithInvariant {
+
+    private static Unsafe unsafe;
+    private static final long BYTE_ARRAY_OFFSET;
+    private static final long CHAR_ARRAY_OFFSET;
+
+    static {
+        unsafe = Utils.getUnsafe();
+        BYTE_ARRAY_OFFSET = unsafe.arrayBaseOffset(byte[].class);
+        CHAR_ARRAY_OFFSET = unsafe.arrayBaseOffset(char[].class);
+    }
+
+    public static void main(String[] args) throws Exception {
+        byte[] byte_array1 = new byte[1000];
+        byte[] byte_array2 = new byte[1000];
+        char[] char_array = new char[1000];
+
+        for (int i = 0; i < 20_000; ++i) {
+            copyByteToChar(byte_array1, byte_array2, char_array, 1);
+            copyCharToByte(char_array, byte_array1, 1);
+            copyCharToByteAligned(char_array, byte_array1);
+            copyCharToByteUnaligned(char_array, byte_array1);
+        }
+    }
+
+    /*
+     * Copy multiple consecutive chars from a byte array to a given offset in a char array
+     * to trigger C2's superword optimization. The offset in the byte array is independent
+     * of the loop induction variable and can be set to an arbitrary value. It may then not
+     * be possible to both align the LoadUS and the StoreC operations. Therefore, vectorization
+     * should only be done in this case if unaligned memory accesses are allowed.
+     */
+    public static void copyByteToChar(byte[] src1, byte[] src2, char[] dst, int off) {
+        off = (int) BYTE_ARRAY_OFFSET + (off << 1);
+        byte[] src = src1;
+        for (int i = (int) CHAR_ARRAY_OFFSET; i < 100; i = i + 8) {
+            // Copy 8 chars from src to dst
+            unsafe.putChar(dst, i + 0, unsafe.getChar(src, off + 0));
+            unsafe.putChar(dst, i + 2, unsafe.getChar(src, off + 2));
+            unsafe.putChar(dst, i + 4, unsafe.getChar(src, off + 4));
+            unsafe.putChar(dst, i + 6, unsafe.getChar(src, off + 6));
+            unsafe.putChar(dst, i + 8, unsafe.getChar(src, off + 8));
+            unsafe.putChar(dst, i + 10, unsafe.getChar(src, off + 10));
+            unsafe.putChar(dst, i + 12, unsafe.getChar(src, off + 12));
+            unsafe.putChar(dst, i + 14, unsafe.getChar(src, off + 14));
+
+            // Prevent loop invariant code motion of char read.
+            src = (src == src1) ? src2 : src1;
+        }
+    }
+
+    /*
+     * Copy multiple consecutive chars from a char array to a given offset in a byte array
+     * to trigger C2's superword optimization. Checks for similar problems as 'copyByteToChar'.
+     */
+    public static void copyCharToByte(char[] src, byte[] dst, int off) {
+        off = (int) BYTE_ARRAY_OFFSET + (off << 1);
+        for (int i = 0; i < 100; i = i + 8) {
+            // Copy 8 chars from src to dst
+            unsafe.putChar(dst, off + 0, src[i + 0]);
+            unsafe.putChar(dst, off + 2, src[i + 1]);
+            unsafe.putChar(dst, off + 4, src[i + 2]);
+            unsafe.putChar(dst, off + 6, src[i + 3]);
+            unsafe.putChar(dst, off + 8, src[i + 4]);
+            unsafe.putChar(dst, off + 10, src[i + 5]);
+            unsafe.putChar(dst, off + 12, src[i + 6]);
+            unsafe.putChar(dst, off + 14, src[i + 7]);
+        }
+    }
+
+    /*
+     * Variant of copyCharToByte with a constant destination array offset.
+     * The loop should always be vectorized because both the LoadUS and StoreC
+     * operations can be aligned.
+     */
+    public static void copyCharToByteAligned(char[] src, byte[] dst) {
+        final int off = (int) BYTE_ARRAY_OFFSET;
+        for (int i = 8; i < 100; i = i + 8) {
+            // Copy 8 chars from src to dst
+            unsafe.putChar(dst, off + 0, src[i + 0]);
+            unsafe.putChar(dst, off + 2, src[i + 1]);
+            unsafe.putChar(dst, off + 4, src[i + 2]);
+            unsafe.putChar(dst, off + 6, src[i + 3]);
+            unsafe.putChar(dst, off + 8, src[i + 4]);
+            unsafe.putChar(dst, off + 10, src[i + 5]);
+            unsafe.putChar(dst, off + 12, src[i + 6]);
+            unsafe.putChar(dst, off + 14, src[i + 7]);
+        }
+    }
+
+    /*
+     * Variant of copyCharToByte with a constant destination array offset. The
+     * loop should only be vectorized if unaligned memory operations are allowed
+     * because not both the LoadUS and the StoreC can be aligned.
+     */
+    public static void copyCharToByteUnaligned(char[] src, byte[] dst) {
+        final int off = (int) BYTE_ARRAY_OFFSET + 2;
+        for (int i = 0; i < 100; i = i + 8) {
+            // Copy 8 chars from src to dst
+            unsafe.putChar(dst, off + 0, src[i + 0]);
+            unsafe.putChar(dst, off + 2, src[i + 1]);
+            unsafe.putChar(dst, off + 4, src[i + 2]);
+            unsafe.putChar(dst, off + 6, src[i + 3]);
+            unsafe.putChar(dst, off + 8, src[i + 4]);
+            unsafe.putChar(dst, off + 10, src[i + 5]);
+            unsafe.putChar(dst, off + 12, src[i + 6]);
+            unsafe.putChar(dst, off + 14, src[i + 7]);
+        }
+    }
+}
--- a/hotspot/test/compiler/oracle/CheckCompileCommandOption.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/oracle/CheckCompileCommandOption.java	Wed Jul 05 20:35:10 2017 +0200
@@ -24,7 +24,7 @@
 import java.io.PrintWriter;
 import java.io.File;
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 /*
  * @test CheckCompileCommandOption
--- a/hotspot/test/compiler/oracle/GetMethodOptionTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/oracle/GetMethodOptionTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -24,14 +24,14 @@
 import java.lang.reflect.Executable;
 import java.util.function.BiFunction;
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 import sun.hotspot.WhiteBox;
 
 /*
  * @test
  * @bug 8074980
  * @library /testlibrary /../../test/lib
- * @build sun.hotspot.WhiteBox com.oracle.java.testlibrary.Asserts GetMethodOptionTest
+ * @build sun.hotspot.WhiteBox jdk.test.lib.Asserts GetMethodOptionTest
  * @run main ClassFileInstaller sun.hotspot.WhiteBox
  *                              sun.hotspot.WhiteBox$WhiteBoxPermission
  * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI
--- a/hotspot/test/compiler/oracle/TestCompileCommand.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/oracle/TestCompileCommand.java	Wed Jul 05 20:35:10 2017 +0200
@@ -24,7 +24,7 @@
 import java.io.PrintWriter;
 import java.io.File;
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 /*
  * @test TestCompileCommand
--- a/hotspot/test/compiler/profiling/spectrapredefineclass/Launcher.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/profiling/spectrapredefineclass/Launcher.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,7 +21,7 @@
  * questions.
  */
 import java.io.PrintWriter;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 /*
  * @test
--- a/hotspot/test/compiler/profiling/spectrapredefineclass_classloaders/Launcher.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/profiling/spectrapredefineclass_classloaders/Launcher.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,7 +21,7 @@
  * questions.
  */
 import java.io.PrintWriter;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 /*
  * @test
--- a/hotspot/test/compiler/rangechecks/TestExplicitRangeChecks.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rangechecks/TestExplicitRangeChecks.java	Wed Jul 05 20:35:10 2017 +0200
@@ -28,7 +28,7 @@
  * @library /testlibrary /../../test/lib /compiler/whitebox
  * @build  TestExplicitRangeChecks
  * @run main ClassFileInstaller sun.hotspot.WhiteBox
- * @run main ClassFileInstaller com.oracle.java.testlibrary.Platform
+ * @run main ClassFileInstaller jdk.test.lib.Platform
  * @run main/othervm -ea -Xmixed -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI
  *                   -XX:-BackgroundCompilation -XX:-UseOnStackReplacement -XX:CompileCommand=compileonly,TestExplicitRangeChecks.test* TestExplicitRangeChecks
  *
@@ -39,7 +39,7 @@
 import java.util.*;
 import sun.hotspot.WhiteBox;
 import sun.hotspot.code.NMethod;
-import com.oracle.java.testlibrary.Platform;
+import jdk.test.lib.Platform;
 import sun.misc.Unsafe;
 
 public class TestExplicitRangeChecks {
--- a/hotspot/test/compiler/rangechecks/TestRangeCheckSmearing.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rangechecks/TestRangeCheckSmearing.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  * @build TestRangeCheckSmearing
  * @run main ClassFileInstaller sun.hotspot.WhiteBox
- * @run main ClassFileInstaller com.oracle.java.testlibrary.Platform
+ * @run main ClassFileInstaller jdk.test.lib.Platform
  * @run main/othervm -ea -Xmixed -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI
  *                   -XX:-BackgroundCompilation -XX:-UseOnStackReplacement TestRangeCheckSmearing
  *
@@ -41,7 +41,7 @@
 import java.util.*;
 import sun.hotspot.WhiteBox;
 import sun.hotspot.code.NMethod;
-import com.oracle.java.testlibrary.Platform;
+import jdk.test.lib.Platform;
 
 public class TestRangeCheckSmearing {
     private static final WhiteBox WHITE_BOX = WhiteBox.getWhiteBox();
--- a/hotspot/test/compiler/rtm/cli/RTMGenericCommandLineOptionTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/cli/RTMGenericCommandLineOptionTest.java	Wed Jul 05 20:35:10 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
@@ -22,8 +22,8 @@
  *
  */
 
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.*;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.*;
 
 import java.util.function.BooleanSupplier;
 
@@ -88,7 +88,7 @@
 
     @Override
     public void runTestCases() throws Throwable {
-        if (Platform.isX86() || Platform.isX64()) {
+        if (Platform.isX86() || Platform.isX64() || Platform.isPPC()) {
             if (Platform.isServer() && !Platform.isEmbedded()) {
                 runX86SupportedVMTestCases();
             } else {
@@ -108,7 +108,7 @@
     }
 
     /**
-     * Runs test cases on non-X86 CPU if VM does not support RTM locking.
+     * Runs test cases on X86 CPU if VM does not support RTM locking.
      * @throws Throwable
      */
     protected void runX86UnsupportedVMTestCases() throws Throwable {
--- a/hotspot/test/compiler/rtm/cli/RTMLockingAwareTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/cli/RTMLockingAwareTest.java	Wed Jul 05 20:35:10 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,9 +25,9 @@
 import java.util.List;
 import java.util.LinkedList;
 
-import com.oracle.java.testlibrary.ExitCode;
-import com.oracle.java.testlibrary.cli.*;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.ExitCode;
+import jdk.test.lib.cli.*;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
 
--- a/hotspot/test/compiler/rtm/cli/TestPrintPreciseRTMLockingStatisticsBase.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/cli/TestPrintPreciseRTMLockingStatisticsBase.java	Wed Jul 05 20:35:10 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
@@ -22,8 +22,8 @@
  *
  */
 
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.*;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.*;
 
 import java.util.function.BooleanSupplier;
 
--- a/hotspot/test/compiler/rtm/cli/TestPrintPreciseRTMLockingStatisticsOptionOnSupportedConfig.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/cli/TestPrintPreciseRTMLockingStatisticsOptionOnSupportedConfig.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,8 +38,8 @@
  *                   TestPrintPreciseRTMLockingStatisticsOptionOnSupportedConfig
  */
 
-import com.oracle.java.testlibrary.cli.*;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.cli.*;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
 
--- a/hotspot/test/compiler/rtm/cli/TestPrintPreciseRTMLockingStatisticsOptionOnUnsupportedConfig.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/cli/TestPrintPreciseRTMLockingStatisticsOptionOnUnsupportedConfig.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,8 +38,8 @@
  *                 TestPrintPreciseRTMLockingStatisticsOptionOnUnsupportedConfig
  */
 
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
-import com.oracle.java.testlibrary.cli.predicate.NotPredicate;
+import jdk.test.lib.cli.predicate.AndPredicate;
+import jdk.test.lib.cli.predicate.NotPredicate;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
 
--- a/hotspot/test/compiler/rtm/cli/TestRTMAbortRatioOptionOnUnsupportedConfig.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/cli/TestRTMAbortRatioOptionOnUnsupportedConfig.java	Wed Jul 05 20:35:10 2017 +0200
@@ -37,8 +37,8 @@
  *                   -XX:+WhiteBoxAPI TestRTMAbortRatioOptionOnUnsupportedConfig
  */
 
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
-import com.oracle.java.testlibrary.cli.predicate.NotPredicate;
+import jdk.test.lib.cli.predicate.AndPredicate;
+import jdk.test.lib.cli.predicate.NotPredicate;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
 
--- a/hotspot/test/compiler/rtm/cli/TestRTMTotalCountIncrRateOptionOnUnsupportedConfig.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/cli/TestRTMTotalCountIncrRateOptionOnUnsupportedConfig.java	Wed Jul 05 20:35:10 2017 +0200
@@ -22,8 +22,8 @@
  *
  */
 
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
-import com.oracle.java.testlibrary.cli.predicate.NotPredicate;
+import jdk.test.lib.cli.predicate.AndPredicate;
+import jdk.test.lib.cli.predicate.NotPredicate;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
 
--- a/hotspot/test/compiler/rtm/cli/TestUseRTMDeoptOptionOnSupportedConfig.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/cli/TestUseRTMDeoptOptionOnSupportedConfig.java	Wed Jul 05 20:35:10 2017 +0200
@@ -37,9 +37,9 @@
  *                   -XX:+WhiteBoxAPI TestUseRTMDeoptOptionOnSupportedConfig
  */
 
-import com.oracle.java.testlibrary.ExitCode;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.ExitCode;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
 
--- a/hotspot/test/compiler/rtm/cli/TestUseRTMDeoptOptionOnUnsupportedConfig.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/cli/TestUseRTMDeoptOptionOnUnsupportedConfig.java	Wed Jul 05 20:35:10 2017 +0200
@@ -37,10 +37,10 @@
  *                   -XX:+WhiteBoxAPI TestUseRTMDeoptOptionOnUnsupportedConfig
  */
 
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.CommandLineOptionTest;
 
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
-import com.oracle.java.testlibrary.cli.predicate.NotPredicate;
+import jdk.test.lib.cli.predicate.AndPredicate;
+import jdk.test.lib.cli.predicate.NotPredicate;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
 
--- a/hotspot/test/compiler/rtm/cli/TestUseRTMForStackLocksOptionOnSupportedConfig.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/cli/TestUseRTMForStackLocksOptionOnSupportedConfig.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,9 +38,9 @@
  *                   TestUseRTMForStackLocksOptionOnSupportedConfig
  */
 
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.*;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.*;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
 
--- a/hotspot/test/compiler/rtm/cli/TestUseRTMForStackLocksOptionOnUnsupportedConfig.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/cli/TestUseRTMForStackLocksOptionOnUnsupportedConfig.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,10 +38,10 @@
  *                    TestUseRTMForStackLocksOptionOnUnsupportedConfig
  */
 
-import com.oracle.java.testlibrary.ExitCode;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
-import com.oracle.java.testlibrary.cli.predicate.NotPredicate;
+import jdk.test.lib.ExitCode;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
+import jdk.test.lib.cli.predicate.NotPredicate;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
 
--- a/hotspot/test/compiler/rtm/cli/TestUseRTMLockingOptionOnSupportedConfig.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/cli/TestUseRTMLockingOptionOnSupportedConfig.java	Wed Jul 05 20:35:10 2017 +0200
@@ -37,9 +37,9 @@
  *                   -XX:+WhiteBoxAPI TestUseRTMLockingOptionOnSupportedConfig
  */
 
-import com.oracle.java.testlibrary.ExitCode;
-import com.oracle.java.testlibrary.cli.*;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.ExitCode;
+import jdk.test.lib.cli.*;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
 
--- a/hotspot/test/compiler/rtm/cli/TestUseRTMLockingOptionOnUnsupportedCPU.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/cli/TestUseRTMLockingOptionOnUnsupportedCPU.java	Wed Jul 05 20:35:10 2017 +0200
@@ -37,10 +37,10 @@
  *                   -XX:+WhiteBoxAPI TestUseRTMLockingOptionOnUnsupportedCPU
  */
 
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.*;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
-import com.oracle.java.testlibrary.cli.predicate.NotPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.*;
+import jdk.test.lib.cli.predicate.AndPredicate;
+import jdk.test.lib.cli.predicate.NotPredicate;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
 
@@ -60,7 +60,7 @@
                 "UseRTMLocking");
         String errorMessage = RTMGenericCommandLineOptionTest.RTM_INSTR_ERROR;
 
-        if (Platform.isX86() || Platform.isX64()) {
+        if (Platform.isX86() || Platform.isX64() || Platform.isPPC()) {
             String shouldFailMessage = "JVM startup should fail with option "
                     + "-XX:+UseRTMLocking on unsupported CPU";
             // verify that we get an error when use +UseRTMLocking
--- a/hotspot/test/compiler/rtm/cli/TestUseRTMLockingOptionOnUnsupportedVM.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/cli/TestUseRTMLockingOptionOnUnsupportedVM.java	Wed Jul 05 20:35:10 2017 +0200
@@ -37,10 +37,10 @@
  *                   -XX:+WhiteBoxAPI TestUseRTMLockingOptionOnUnsupportedVM
  */
 
-import com.oracle.java.testlibrary.ExitCode;
-import com.oracle.java.testlibrary.cli.*;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
-import com.oracle.java.testlibrary.cli.predicate.NotPredicate;
+import jdk.test.lib.ExitCode;
+import jdk.test.lib.cli.*;
+import jdk.test.lib.cli.predicate.AndPredicate;
+import jdk.test.lib.cli.predicate.NotPredicate;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
 
--- a/hotspot/test/compiler/rtm/cli/TestUseRTMLockingOptionWithBiasedLocking.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/cli/TestUseRTMLockingOptionWithBiasedLocking.java	Wed Jul 05 20:35:10 2017 +0200
@@ -37,9 +37,9 @@
  *                   -XX:+WhiteBoxAPI TestUseRTMLockingOptionWithBiasedLocking
  */
 
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.*;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.*;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
 
--- a/hotspot/test/compiler/rtm/locking/TestRTMAbortRatio.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/locking/TestRTMAbortRatio.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,9 +38,9 @@
  */
 
 import java.util.List;
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.*;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
--- a/hotspot/test/compiler/rtm/locking/TestRTMAbortThreshold.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/locking/TestRTMAbortThreshold.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,9 +38,9 @@
  */
 
 import java.util.List;
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.*;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
--- a/hotspot/test/compiler/rtm/locking/TestRTMAfterNonRTMDeopt.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/locking/TestRTMAfterNonRTMDeopt.java	Wed Jul 05 20:35:10 2017 +0200
@@ -40,9 +40,9 @@
  */
 
 import java.util.List;
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.*;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
--- a/hotspot/test/compiler/rtm/locking/TestRTMDeoptOnHighAbortRatio.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/locking/TestRTMDeoptOnHighAbortRatio.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,9 +38,9 @@
  */
 
 import java.util.List;
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.*;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
--- a/hotspot/test/compiler/rtm/locking/TestRTMDeoptOnLowAbortRatio.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/locking/TestRTMDeoptOnLowAbortRatio.java	Wed Jul 05 20:35:10 2017 +0200
@@ -37,9 +37,9 @@
  */
 
 import java.util.List;
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.*;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
--- a/hotspot/test/compiler/rtm/locking/TestRTMLockingCalculationDelay.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/locking/TestRTMLockingCalculationDelay.java	Wed Jul 05 20:35:10 2017 +0200
@@ -37,9 +37,9 @@
  *                   -XX:+WhiteBoxAPI TestRTMLockingCalculationDelay
  */
 
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.*;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
--- a/hotspot/test/compiler/rtm/locking/TestRTMLockingThreshold.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/locking/TestRTMLockingThreshold.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,9 +38,9 @@
  */
 
 import java.util.List;
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.*;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
--- a/hotspot/test/compiler/rtm/locking/TestRTMRetryCount.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/locking/TestRTMRetryCount.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,9 +38,9 @@
 
 import java.util.List;
 
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.*;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
--- a/hotspot/test/compiler/rtm/locking/TestRTMSpinLoopCount.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/locking/TestRTMSpinLoopCount.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,9 +38,9 @@
  */
 
 import java.util.List;
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.*;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
--- a/hotspot/test/compiler/rtm/locking/TestRTMTotalCountIncrRate.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/locking/TestRTMTotalCountIncrRate.java	Wed Jul 05 20:35:10 2017 +0200
@@ -40,9 +40,9 @@
 import sun.misc.Unsafe;
 import java.util.List;
 
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.*;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
--- a/hotspot/test/compiler/rtm/locking/TestUseRTMAfterLockInflation.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/locking/TestUseRTMAfterLockInflation.java	Wed Jul 05 20:35:10 2017 +0200
@@ -39,9 +39,9 @@
 
 import java.util.List;
 
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.*;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
--- a/hotspot/test/compiler/rtm/locking/TestUseRTMDeopt.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/locking/TestUseRTMDeopt.java	Wed Jul 05 20:35:10 2017 +0200
@@ -37,9 +37,9 @@
  *                   -XX:+WhiteBoxAPI TestUseRTMDeopt
  */
 
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.*;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
--- a/hotspot/test/compiler/rtm/locking/TestUseRTMForInflatedLocks.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/locking/TestUseRTMForInflatedLocks.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,9 +38,9 @@
 
 import java.util.List;
 
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.*;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
--- a/hotspot/test/compiler/rtm/locking/TestUseRTMForStackLocks.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/locking/TestUseRTMForStackLocks.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,9 +38,9 @@
 
 import java.util.List;
 
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.*;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
--- a/hotspot/test/compiler/rtm/locking/TestUseRTMXendForLockBusy.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/locking/TestUseRTMXendForLockBusy.java	Wed Jul 05 20:35:10 2017 +0200
@@ -39,9 +39,9 @@
 
 import java.util.List;
 
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.*;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
--- a/hotspot/test/compiler/rtm/method_options/TestNoRTMLockElidingOption.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/method_options/TestNoRTMLockElidingOption.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,9 +38,9 @@
  */
 
 import java.util.List;
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.*;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
--- a/hotspot/test/compiler/rtm/method_options/TestUseRTMLockElidingOption.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/method_options/TestUseRTMLockElidingOption.java	Wed Jul 05 20:35:10 2017 +0200
@@ -39,9 +39,9 @@
  */
 
 import java.util.List;
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.*;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
--- a/hotspot/test/compiler/rtm/print/TestPrintPreciseRTMLockingStatistics.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/rtm/print/TestPrintPreciseRTMLockingStatistics.java	Wed Jul 05 20:35:10 2017 +0200
@@ -41,9 +41,9 @@
 
 import java.util.*;
 
-import com.oracle.java.testlibrary.*;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
+import jdk.test.lib.*;
+import jdk.test.lib.cli.CommandLineOptionTest;
+import jdk.test.lib.cli.predicate.AndPredicate;
 import rtm.*;
 import rtm.predicate.SupportedCPU;
 import rtm.predicate.SupportedVM;
--- a/hotspot/test/compiler/startup/NumCompilerThreadsCheck.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/startup/NumCompilerThreadsCheck.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,7 +29,7 @@
  * @modules java.base/sun.misc
  *          java.management
  */
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class NumCompilerThreadsCheck {
 
--- a/hotspot/test/compiler/startup/SmallCodeCacheStartup.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/startup/SmallCodeCacheStartup.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,8 +31,8 @@
  * @modules java.base/sun.misc
  *          java.management
  */
-import com.oracle.java.testlibrary.*;
-import static com.oracle.java.testlibrary.Asserts.assertTrue;
+import jdk.test.lib.*;
+import static jdk.test.lib.Asserts.assertTrue;
 
 public class SmallCodeCacheStartup {
     public static void main(String[] args) throws Exception {
--- a/hotspot/test/compiler/startup/StartupOutput.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/startup/StartupOutput.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,7 +29,7 @@
  * @modules java.base/sun.misc
  *          java.management
  */
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class StartupOutput {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/compiler/testlibrary/CompilerUtils.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/testlibrary/CompilerUtils.java	Wed Jul 05 20:35:10 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
@@ -21,8 +21,8 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.Platform;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.Platform;
 import java.util.stream.IntStream;
 import sun.hotspot.WhiteBox;
 
--- a/hotspot/test/compiler/testlibrary/rtm/AbortProvoker.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/testlibrary/rtm/AbortProvoker.java	Wed Jul 05 20:35:10 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
@@ -28,7 +28,7 @@
 import java.util.concurrent.BrokenBarrierException;
 import java.util.concurrent.CyclicBarrier;
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 import sun.hotspot.WhiteBox;
 
 /**
--- a/hotspot/test/compiler/testlibrary/rtm/AbortType.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/testlibrary/rtm/AbortType.java	Wed Jul 05 20:35:10 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
@@ -24,7 +24,7 @@
 
 package rtm;
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 
 import java.util.HashMap;
 import java.util.Map;
--- a/hotspot/test/compiler/testlibrary/rtm/RTMTestBase.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/testlibrary/rtm/RTMTestBase.java	Wed Jul 05 20:35:10 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
@@ -34,10 +34,10 @@
 import java.util.regex.Matcher;
 import java.util.regex.Pattern;
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
-import com.oracle.java.testlibrary.Utils;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
+import jdk.test.lib.Utils;
+import jdk.test.lib.cli.CommandLineOptionTest;
 
 /**
  * Auxiliary methods used for RTM testing.
--- a/hotspot/test/compiler/testlibrary/rtm/XAbortProvoker.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/testlibrary/rtm/XAbortProvoker.java	Wed Jul 05 20:35:10 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
@@ -24,7 +24,7 @@
 
 package rtm;
 
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Utils;
 import sun.misc.Unsafe;
 
 /**
--- a/hotspot/test/compiler/testlibrary/rtm/predicate/SupportedCPU.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/testlibrary/rtm/predicate/SupportedCPU.java	Wed Jul 05 20:35:10 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
@@ -28,9 +28,12 @@
 
 import java.util.function.BooleanSupplier;
 
+import jdk.test.lib.Platform;
+
 public class SupportedCPU implements BooleanSupplier {
     @Override
     public boolean getAsBoolean() {
+        if (Platform.isPPC()) { return CPUInfo.hasFeature("tcheck"); }
         return CPUInfo.hasFeature("rtm");
     }
 }
--- a/hotspot/test/compiler/testlibrary/rtm/predicate/SupportedVM.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/testlibrary/rtm/predicate/SupportedVM.java	Wed Jul 05 20:35:10 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
@@ -24,7 +24,7 @@
 
 package rtm.predicate;
 
-import com.oracle.java.testlibrary.Platform;
+import jdk.test.lib.Platform;
 
 import java.util.function.BooleanSupplier;
 
--- a/hotspot/test/compiler/testlibrary/sha/predicate/IntrinsicPredicates.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/testlibrary/sha/predicate/IntrinsicPredicates.java	Wed Jul 05 20:35:10 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
@@ -23,10 +23,10 @@
 
 package sha.predicate;
 
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.cli.predicate.AndPredicate;
-import com.oracle.java.testlibrary.cli.predicate.CPUSpecificPredicate;
-import com.oracle.java.testlibrary.cli.predicate.OrPredicate;
+import jdk.test.lib.Platform;
+import jdk.test.lib.cli.predicate.AndPredicate;
+import jdk.test.lib.cli.predicate.CPUSpecificPredicate;
+import jdk.test.lib.cli.predicate.OrPredicate;
 import sun.hotspot.WhiteBox;
 
 import java.util.function.BooleanSupplier;
--- a/hotspot/test/compiler/testlibrary/uncommontrap/Verifier.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/testlibrary/uncommontrap/Verifier.java	Wed Jul 05 20:35:10 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
@@ -33,7 +33,7 @@
 import java.util.Properties;
 import java.util.regex.Pattern;
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 /**
  * Utility tool aimed to verify presence or absence of specified uncommon trap
  * in compilation log.
--- a/hotspot/test/compiler/tiered/TransitionsTestExecutor.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/tiered/TransitionsTestExecutor.java	Wed Jul 05 20:35:10 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
@@ -21,8 +21,8 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 
 import java.lang.management.ManagementFactory;
 import java.lang.management.RuntimeMXBean;
--- a/hotspot/test/compiler/types/correctness/CorrectnessTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/types/correctness/CorrectnessTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -54,8 +54,8 @@
  * @summary Tests correctness of type usage with type profiling and speculations
  */
 
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.Platform;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.Platform;
 import execution.Execution;
 import execution.MethodHandleDelegate;
 import execution.TypeConflict;
--- a/hotspot/test/compiler/types/correctness/OffTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/types/correctness/OffTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -37,9 +37,9 @@
  * @run main/timeout=1200 OffTest
  */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
+import jdk.test.lib.Utils;
 import java.util.Random;
 import scenarios.ProfilingType;
 
--- a/hotspot/test/compiler/types/correctness/scenarios/ArrayScenario.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/types/correctness/scenarios/ArrayScenario.java	Wed Jul 05 20:35:10 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
@@ -23,7 +23,7 @@
 
 package scenarios;
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 import hierarchies.TypeHierarchy;
 
 import java.lang.reflect.Array;
--- a/hotspot/test/compiler/types/correctness/scenarios/CheckCast.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/types/correctness/scenarios/CheckCast.java	Wed Jul 05 20:35:10 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
@@ -23,7 +23,7 @@
 
 package scenarios;
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 import hierarchies.TypeHierarchy;
 
 import java.util.Objects;
--- a/hotspot/test/compiler/types/correctness/scenarios/ClassIdentity.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/types/correctness/scenarios/ClassIdentity.java	Wed Jul 05 20:35:10 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
@@ -23,7 +23,7 @@
 
 package scenarios;
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 import hierarchies.TypeHierarchy;
 
 /**
--- a/hotspot/test/compiler/types/correctness/scenarios/ClassInstanceOf.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/types/correctness/scenarios/ClassInstanceOf.java	Wed Jul 05 20:35:10 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
@@ -23,7 +23,7 @@
 
 package scenarios;
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 import hierarchies.TypeHierarchy;
 
 /**
--- a/hotspot/test/compiler/types/correctness/scenarios/ClassIsInstance.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/types/correctness/scenarios/ClassIsInstance.java	Wed Jul 05 20:35:10 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
@@ -23,7 +23,7 @@
 
 package scenarios;
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 import hierarchies.TypeHierarchy;
 
 /**
--- a/hotspot/test/compiler/types/correctness/scenarios/ReceiverAtInvokes.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/types/correctness/scenarios/ReceiverAtInvokes.java	Wed Jul 05 20:35:10 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
@@ -23,7 +23,7 @@
 
 package scenarios;
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 import hierarchies.TypeHierarchy;
 
 /**
--- a/hotspot/test/compiler/uncommontrap/TestUnstableIfTrap.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/uncommontrap/TestUnstableIfTrap.java	Wed Jul 05 20:35:10 2017 +0200
@@ -26,8 +26,8 @@
 import java.lang.reflect.Method;
 import java.util.Properties;
 
-import com.oracle.java.testlibrary.ByteCodeLoader;
-import com.oracle.java.testlibrary.Platform;
+import jdk.test.lib.ByteCodeLoader;
+import jdk.test.lib.Platform;
 import jdk.internal.org.objectweb.asm.ClassVisitor;
 import jdk.internal.org.objectweb.asm.ClassWriter;
 import jdk.internal.org.objectweb.asm.Label;
@@ -46,7 +46,7 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build TestUnstableIfTrap com.oracle.java.testlibrary.* uncommontrap.Verifier
+ * @build TestUnstableIfTrap jdk.test.lib.* uncommontrap.Verifier
  * @run main ClassFileInstaller sun.hotspot.WhiteBox
  *                              sun.hotspot.WhiteBox$WhiteBoxPermission
  * @run main/othervm -Xbatch -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions
--- a/hotspot/test/compiler/unsafe/UnsafeRaw.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/unsafe/UnsafeRaw.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  * @run main/othervm -Xbatch UnsafeRaw
  */
 
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Utils;
 import java.util.Random;
 
 public class UnsafeRaw {
--- a/hotspot/test/compiler/whitebox/AllocationCodeBlobTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/whitebox/AllocationCodeBlobTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -28,8 +28,8 @@
 
 import sun.hotspot.WhiteBox;
 import sun.hotspot.code.BlobType;
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.InfiniteLoop;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.InfiniteLoop;
 
 /*
  * @test AllocationCodeBlobTest
--- a/hotspot/test/compiler/whitebox/DeoptimizeFramesTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/whitebox/DeoptimizeFramesTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -46,8 +46,8 @@
 import java.util.concurrent.Phaser;
 
 import sun.hotspot.code.NMethod;
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.InfiniteLoop;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.InfiniteLoop;
 
 public class DeoptimizeFramesTest extends CompilerWhiteBoxTest {
     private final boolean makeNotEntrant;
--- a/hotspot/test/compiler/whitebox/ForceNMethodSweepTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/whitebox/ForceNMethodSweepTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -28,8 +28,8 @@
 import sun.hotspot.WhiteBox;
 import sun.hotspot.code.BlobType;
 
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.InfiniteLoop;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.InfiniteLoop;
 
 /*
  * @test
--- a/hotspot/test/compiler/whitebox/GetCodeHeapEntriesTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/whitebox/GetCodeHeapEntriesTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -28,7 +28,7 @@
 import sun.hotspot.WhiteBox;
 import sun.hotspot.code.CodeBlob;
 import sun.hotspot.code.BlobType;
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 
 /*
  * @test GetCodeHeapEntriesTest
--- a/hotspot/test/compiler/whitebox/GetNMethodTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/whitebox/GetNMethodTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -24,7 +24,7 @@
 
 import sun.hotspot.code.BlobType;
 import sun.hotspot.code.NMethod;
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 
 /*
  * @test GetNMethodTest
--- a/hotspot/test/compiler/whitebox/IsMethodCompilableTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/whitebox/IsMethodCompilableTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -24,19 +24,20 @@
 /*
  * @test IsMethodCompilableTest
  * @bug 8007270 8006683 8007288 8022832
- * @library /testlibrary /../../test/lib /testlibrary/com/oracle/java/testlibrary
+ * @library /testlibrary /../../test/lib
  * @modules java.base/sun.misc
  *          java.management
+ * @build jdk.test.lib.* sun.hotspot.WhiteBox
  * @build IsMethodCompilableTest
  * @run main ClassFileInstaller sun.hotspot.WhiteBox
  *                              sun.hotspot.WhiteBox$WhiteBoxPermission
- * @run main ClassFileInstaller com.oracle.java.testlibrary.Platform
+ * @run main ClassFileInstaller jdk.test.lib.Platform
  * @run main/othervm/timeout=2400 -Xbootclasspath/a:. -Xmixed -XX:-TieredCompilation -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI -XX:PerMethodRecompilationCutoff=3 -XX:CompileCommand=compileonly,SimpleTestCase$Helper::* IsMethodCompilableTest
  * @summary testing of WB::isMethodCompilable()
  * @author igor.ignatyev@oracle.com
  */
 
-import com.oracle.java.testlibrary.Platform;
+import jdk.test.lib.Platform;
 
 public class IsMethodCompilableTest extends CompilerWhiteBoxTest {
     /**
--- a/hotspot/test/compiler/whitebox/LockCompilationTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/compiler/whitebox/LockCompilationTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,7 +38,7 @@
 import java.util.concurrent.BrokenBarrierException;
 import java.util.concurrent.CyclicBarrier;
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 
 public class LockCompilationTest extends CompilerWhiteBoxTest {
     public static void main(String[] args) throws Exception {
--- a/hotspot/test/gc/6941923/Test6941923.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/6941923/Test6941923.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  * @run main/othervm/timeout=600 Test6941923
  *
  */
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import java.io.File;
 import java.io.FilenameFilter;
 import java.util.ArrayList;
--- a/hotspot/test/gc/TestCardTablePageCommits.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/TestCardTablePageCommits.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,10 +21,10 @@
 * questions.
 */
 
-import com.oracle.java.testlibrary.JDKToolFinder;
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
-import com.oracle.java.testlibrary.Platform;
+import jdk.test.lib.JDKToolFinder;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
+import jdk.test.lib.Platform;
 
 /*
  * @test TestCardTablePageCommits
--- a/hotspot/test/gc/TestDisableExplicitGC.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/TestDisableExplicitGC.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  */
 import java.lang.management.GarbageCollectorMXBean;
 import java.util.List;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class TestDisableExplicitGC {
 
--- a/hotspot/test/gc/TestGCLogRotationViaJcmd.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/TestGCLogRotationViaJcmd.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  * @run main/othervm -Xloggc:test.log -XX:+UseGCLogFileRotation -XX:NumberOfGCLogFiles=3 TestGCLogRotationViaJcmd
  *
  */
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import java.io.File;
 import java.io.FilenameFilter;
 
--- a/hotspot/test/gc/TestObjectAlignment.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/TestObjectAlignment.java	Wed Jul 05 20:35:10 2017 +0200
@@ -43,8 +43,8 @@
  * @run main/othervm TestObjectAlignment -Xmx20M -XX:-ExplicitGCInvokesConcurrent -XX:+IgnoreUnrecognizedVMOptions -XX:ObjectAlignmentInBytes=256
  */
 
-import com.oracle.java.testlibrary.ProcessTools;
-import com.oracle.java.testlibrary.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
 
 public class TestObjectAlignment {
 
--- a/hotspot/test/gc/TestSmallHeap.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/TestSmallHeap.java	Wed Jul 05 20:35:10 2017 +0200
@@ -57,10 +57,10 @@
  * So, the expected heap size is page_size * 512.
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import com.sun.management.HotSpotDiagnosticMXBean;
 import java.lang.management.ManagementFactory;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 import sun.hotspot.WhiteBox;
 
--- a/hotspot/test/gc/TestSoftReferencesBehaviorOnOOME.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/TestSoftReferencesBehaviorOnOOME.java	Wed Jul 05 20:35:10 2017 +0200
@@ -28,29 +28,30 @@
  * @library /testlibrary
  * @modules java.base/sun.misc
  *          java.management
- * @ignore 8073669
  * @build TestSoftReferencesBehaviorOnOOME
  * @run main/othervm -Xmx128m TestSoftReferencesBehaviorOnOOME 512 2k
  * @run main/othervm -Xmx128m TestSoftReferencesBehaviorOnOOME 128k 256k
- * @run main/othervm -Xmx128m TestSoftReferencesBehaviorOnOOME 2k 32k 10
+ * @run main/othervm -Xmx128m TestSoftReferencesBehaviorOnOOME 2k 32k
  */
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Utils;
+import jdk.test.lib.Asserts;
 import java.lang.ref.SoftReference;
 import java.util.LinkedList;
 import java.util.Random;
 
 public class TestSoftReferencesBehaviorOnOOME {
 
-    private static final Random rndGenerator = Utils.getRandomInstance();
-
+    /**
+     * Test generates a lot of soft references to objects with random payloads.
+     * Then it provokes OOME and checks that all SoftReferences has been gone
+     * @param args - [minSize] [maxSize] [freq]
+     *  where
+     *  - minSize - min size of random objects
+     *  - maxSize - max size of random objects
+     */
     public static void main(String[] args) {
-        int semiRefAllocFrequency = DEFAULT_FREQUENCY;
-        long minSize = DEFAULT_MIN_SIZE,
-                maxSize = DEFAULT_MAX_SIZE;
-
-        if ( args.length >= 3 ) {
-            semiRefAllocFrequency = Integer.parseInt(args[2]);
-        }
+        long minSize = DEFAULT_MIN_SIZE;
+        long maxSize = DEFAULT_MAX_SIZE;
 
         if ( args.length >= 2) {
             maxSize = getBytesCount(args[1]);
@@ -60,46 +61,49 @@
             minSize = getBytesCount(args[0]);
         }
 
-        new TestSoftReferencesBehaviorOnOOME().softReferencesOom(minSize, maxSize, semiRefAllocFrequency);
+        new TestSoftReferencesBehaviorOnOOME().softReferencesOom(minSize, maxSize);
     }
 
     /**
      * Test that all SoftReferences has been cleared at time of OOM.
      */
-    void softReferencesOom(long minSize, long maxSize, int semiRefAllocFrequency) {
-        System.out.format( "minSize = %d, maxSize = %d, freq = %d%n", minSize, maxSize, semiRefAllocFrequency );
-        long counter = 0;
+    void softReferencesOom(long minSize, long maxSize) {
+        System.out.format( "minSize = %d, maxSize = %d%n", minSize, maxSize );
+
+        LinkedList<SoftReference> arrSoftRefs = new LinkedList();
+        staticRef = arrSoftRefs;
+        LinkedList arrObjects = new LinkedList();
+        staticRef = arrObjects;
 
         long multiplier = maxSize - minSize;
-        LinkedList<SoftReference> arrSoftRefs = new LinkedList();
-        LinkedList arrObjects = new LinkedList();
         long numberOfNotNulledObjects = 0;
-        long oomSoftArraySize = 0;
 
         try {
-            while (true) {
-                // Keep every Xth object to make sure we hit OOM pretty fast
-                if (counter % semiRefAllocFrequency != 0) {
-                    long allocationSize = ((int) (rndGenerator.nextDouble() * multiplier))
-                            + minSize;
-                    arrObjects.add(new byte[(int)allocationSize]);
-                } else {
-                    arrSoftRefs.add(new SoftReference(new Object()));
-                }
+
+            // Lets allocate as many as we can - taking size of all SoftRerefences
+            // by minimum. So it can provoke some GC but we surely will allocate enough.
+            long numSofts = (long) ((0.95 * Runtime.getRuntime().totalMemory()) / minSize);
+            System.out.println("num Soft: " + numSofts);
+
+            while (numSofts-- > 0) {
+                int allocationSize = ((int) (RND_GENERATOR.nextDouble() * multiplier))
+                            + (int)minSize;
+                arrSoftRefs.add(new SoftReference(new byte[allocationSize]));
+            }
 
-                counter++;
-                if (counter == Long.MAX_VALUE) {
-                    counter = 0;
-                }
+            System.out.println("free: " + Runtime.getRuntime().freeMemory());
+
+            // provoke OOME.
+            while (true) {
+                arrObjects.add(new byte[(int) Runtime.getRuntime().totalMemory()]);
             }
+
         } catch (OutOfMemoryError oome) {
+
             // Clear allocated ballast, so we don't get another OOM.
-
+            staticRef = null;
             arrObjects = null;
-
-            // Get the number of soft refs first, so we don't trigger
-            // another OOM.
-            oomSoftArraySize = arrSoftRefs.size();
+            long oomSoftArraySize = arrSoftRefs.size();
 
             for (SoftReference sr : arrSoftRefs) {
                 Object o = sr.get();
@@ -111,15 +115,14 @@
 
             // Make sure we clear all refs before we return failure
             arrSoftRefs = null;
-
-            if (numberOfNotNulledObjects > 0) {
-                throw new RuntimeException(numberOfNotNulledObjects + " out of "
-                        + oomSoftArraySize + " SoftReferences was not "
-                        + "null at time of OutOfMemoryError");
-            }
+            Asserts.assertFalse(numberOfNotNulledObjects > 0,
+                    "" + numberOfNotNulledObjects + " out of "
+                    + oomSoftArraySize + " SoftReferences was not "
+                    + "null at time of OutOfMemoryError"
+            );
         } finally {
-            arrSoftRefs = null;
-            arrObjects = null;
+            Asserts.assertTrue(arrObjects == null, "OOME hasn't been provoked");
+            Asserts.assertTrue(arrSoftRefs == null, "OOME hasn't been provoked");
         }
     }
 
@@ -128,9 +131,7 @@
         long mod = 1;
 
         if (arg.trim().length() >= 2) {
-            mod = postfixes.indexOf(
-                    arg.trim().charAt(arg.length() - 1)
-            );
+            mod = postfixes.indexOf(arg.trim().charAt(arg.length() - 1));
 
             if (mod != -1) {
                 mod = (long) Math.pow(1024, mod+1);
@@ -143,7 +144,8 @@
         return Long.parseLong(arg) * mod;
     }
 
+    private static final Random RND_GENERATOR = Utils.getRandomInstance();
     private static final long DEFAULT_MIN_SIZE = 512;
     private static final long DEFAULT_MAX_SIZE = 1024;
-    private static final int DEFAULT_FREQUENCY = 4;
+    private static Object staticRef; // to prevent compile optimisations
 }
--- a/hotspot/test/gc/TestVerifyDuringStartup.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/TestVerifyDuringStartup.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,9 +30,9 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.JDKToolFinder;
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.JDKToolFinder;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 import java.util.ArrayList;
 import java.util.Collections;
 
--- a/hotspot/test/gc/TestVerifySilently.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/TestVerifySilently.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,8 +30,8 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 import java.util.ArrayList;
 import java.util.Collections;
 
--- a/hotspot/test/gc/arguments/TestArrayAllocatorMallocLimit.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/arguments/TestArrayAllocatorMallocLimit.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,9 +33,9 @@
  * @run driver TestArrayAllocatorMallocLimit
  */
 
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 import java.math.BigInteger;
 
 public class TestArrayAllocatorMallocLimit {
--- a/hotspot/test/gc/arguments/TestCompressedClassFlags.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/arguments/TestCompressedClassFlags.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 /*
  * @test
--- a/hotspot/test/gc/arguments/TestDynMaxHeapFreeRatio.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/arguments/TestDynMaxHeapFreeRatio.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,10 +21,10 @@
  * questions.
  */
 
-import static com.oracle.java.testlibrary.Asserts.assertEQ;
-import static com.oracle.java.testlibrary.Asserts.assertFalse;
-import static com.oracle.java.testlibrary.Asserts.assertTrue;
-import com.oracle.java.testlibrary.DynamicVMOption;
+import static jdk.test.lib.Asserts.assertEQ;
+import static jdk.test.lib.Asserts.assertFalse;
+import static jdk.test.lib.Asserts.assertTrue;
+import jdk.test.lib.DynamicVMOption;
 
 /**
  * @test TestDynMaxHeapFreeRatio
--- a/hotspot/test/gc/arguments/TestDynMinHeapFreeRatio.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/arguments/TestDynMinHeapFreeRatio.java	Wed Jul 05 20:35:10 2017 +0200
@@ -34,10 +34,10 @@
  * @run main/othervm -XX:MinHeapFreeRatio=51 -XX:MaxHeapFreeRatio=52 TestDynMinHeapFreeRatio
  * @run main/othervm -XX:MinHeapFreeRatio=75 -XX:MaxHeapFreeRatio=100 TestDynMinHeapFreeRatio
  */
-import static com.oracle.java.testlibrary.Asserts.assertEQ;
-import static com.oracle.java.testlibrary.Asserts.assertFalse;
-import static com.oracle.java.testlibrary.Asserts.assertTrue;
-import com.oracle.java.testlibrary.DynamicVMOption;
+import static jdk.test.lib.Asserts.assertEQ;
+import static jdk.test.lib.Asserts.assertFalse;
+import static jdk.test.lib.Asserts.assertTrue;
+import jdk.test.lib.DynamicVMOption;
 
 public class TestDynMinHeapFreeRatio {
 
--- a/hotspot/test/gc/arguments/TestG1ConcRefinementThreads.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/arguments/TestG1ConcRefinementThreads.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import java.util.*;
 import java.util.regex.*;
 
--- a/hotspot/test/gc/arguments/TestG1PercentageOptions.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/arguments/TestG1PercentageOptions.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  * @run driver TestG1PercentageOptions
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class TestG1PercentageOptions {
 
--- a/hotspot/test/gc/arguments/TestHeapFreeRatio.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/arguments/TestHeapFreeRatio.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  * @run main/othervm TestHeapFreeRatio
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class TestHeapFreeRatio {
 
--- a/hotspot/test/gc/arguments/TestInitialTenuringThreshold.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/arguments/TestInitialTenuringThreshold.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
  * @author thomas.schatzl@oracle.com
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class TestInitialTenuringThreshold {
 
--- a/hotspot/test/gc/arguments/TestMaxHeapSizeTools.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/arguments/TestMaxHeapSizeTools.java	Wed Jul 05 20:35:10 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
@@ -26,7 +26,7 @@
 import java.util.ArrayList;
 import java.util.Arrays;
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.hotspot.WhiteBox;
 
 class ErgoArgsPrinter {
--- a/hotspot/test/gc/arguments/TestMaxNewSize.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/arguments/TestMaxNewSize.java	Wed Jul 05 20:35:10 2017 +0200
@@ -46,7 +46,7 @@
 import java.util.ArrayList;
 import java.util.Arrays;
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class TestMaxNewSize {
 
--- a/hotspot/test/gc/arguments/TestObjectTenuringFlags.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/arguments/TestObjectTenuringFlags.java	Wed Jul 05 20:35:10 2017 +0200
@@ -34,7 +34,7 @@
  * @run main/othervm TestObjectTenuringFlags
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 import java.util.*;
 
--- a/hotspot/test/gc/arguments/TestParallelGCThreads.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/arguments/TestParallelGCThreads.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  * @run driver TestParallelGCThreads
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class TestParallelGCThreads {
 
--- a/hotspot/test/gc/arguments/TestSelectDefaultGC.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/arguments/TestSelectDefaultGC.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  * @run driver TestSelectDefaultGC
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import java.util.regex.*;
 
 public class TestSelectDefaultGC {
--- a/hotspot/test/gc/arguments/TestSurvivorAlignmentInBytesOption.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/arguments/TestSurvivorAlignmentInBytesOption.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,8 +21,8 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.ExitCode;
-import com.oracle.java.testlibrary.cli.CommandLineOptionTest;
+import jdk.test.lib.ExitCode;
+import jdk.test.lib.cli.CommandLineOptionTest;
 
 /**
  * @test
--- a/hotspot/test/gc/arguments/TestUnrecognizedVMOptionsHandling.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/arguments/TestUnrecognizedVMOptionsHandling.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  * @run main/othervm TestUnrecognizedVMOptionsHandling
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class TestUnrecognizedVMOptionsHandling {
 
--- a/hotspot/test/gc/arguments/TestUseCompressedOopsErgoTools.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/arguments/TestUseCompressedOopsErgoTools.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,7 +29,7 @@
 import java.util.ArrayList;
 import java.util.Arrays;
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import java.lang.management.ManagementFactory;
 import sun.hotspot.WhiteBox;
 
--- a/hotspot/test/gc/arguments/TestUseNUMAInterleaving.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/arguments/TestUseNUMAInterleaving.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,8 +32,8 @@
  *          java.management
  * @run driver TestUseNUMAInterleaving
  */
-import com.oracle.java.testlibrary.ProcessTools;
-import com.oracle.java.testlibrary.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
 
 public class TestUseNUMAInterleaving {
 
--- a/hotspot/test/gc/arguments/TestVerifyBeforeAndAfterGCFlags.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/arguments/TestVerifyBeforeAndAfterGCFlags.java	Wed Jul 05 20:35:10 2017 +0200
@@ -36,9 +36,9 @@
 import java.util.ArrayList;
 import java.util.Collections;
 
-import com.oracle.java.testlibrary.Utils;
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.Utils;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 
 public class TestVerifyBeforeAndAfterGCFlags {
 
--- a/hotspot/test/gc/class_unloading/TestCMSClassUnloadingEnabledHWM.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/class_unloading/TestCMSClassUnloadingEnabledHWM.java	Wed Jul 05 20:35:10 2017 +0200
@@ -35,8 +35,8 @@
  * @summary Test that -XX:-CMSClassUnloadingEnabled will trigger a Full GC when more than MetaspaceSize metadata is allocated.
  */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 import java.lang.management.GarbageCollectorMXBean;
 import java.lang.management.ManagementFactory;
 import java.util.ArrayList;
--- a/hotspot/test/gc/class_unloading/TestG1ClassUnloadingHWM.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/class_unloading/TestG1ClassUnloadingHWM.java	Wed Jul 05 20:35:10 2017 +0200
@@ -35,8 +35,8 @@
  * @summary Test that -XX:-ClassUnloadingWithConcurrentMark will trigger a Full GC when more than MetaspaceSize metadata is allocated.
  */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 import java.util.ArrayList;
 import java.util.Arrays;
 import sun.hotspot.WhiteBox;
--- a/hotspot/test/gc/concurrentMarkSweep/GuardShrinkWarning.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/concurrentMarkSweep/GuardShrinkWarning.java	Wed Jul 05 20:35:10 2017 +0200
@@ -34,7 +34,7 @@
  * @author jon.masamitsu@oracle.com
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class GuardShrinkWarning {
   public static void main(String args[]) throws Exception {
--- a/hotspot/test/gc/defnew/HeapChangeLogging.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/defnew/HeapChangeLogging.java	Wed Jul 05 20:35:10 2017 +0200
@@ -35,7 +35,7 @@
 import java.util.regex.Matcher;
 import java.util.regex.Pattern;
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class HeapChangeLogging {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/gc/ergonomics/TestDynamicNumberOfGCThreads.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/ergonomics/TestDynamicNumberOfGCThreads.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,8 +30,8 @@
  * @library /testlibrary
  */
 
-import com.oracle.java.testlibrary.ProcessTools;
-import com.oracle.java.testlibrary.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
 
 public class TestDynamicNumberOfGCThreads {
   public static void main(String[] args) throws Exception {
@@ -44,14 +44,24 @@
   }
 
   private static void verifyDynamicNumberOfGCThreads(OutputAnalyzer output) {
+    output.shouldHaveExitValue(0); // test should run succesfully
     output.shouldContain("new_active_workers");
-    output.shouldHaveExitValue(0);
   }
 
   private static void testDynamicNumberOfGCThreads(String gcFlag) throws Exception {
     // UseDynamicNumberOfGCThreads and TraceDynamicGCThreads enabled
-    ProcessBuilder pb_enabled =
-      ProcessTools.createJavaProcessBuilder("-XX:+" + gcFlag, "-Xmx10M", "-XX:+PrintGCDetails",  "-XX:+UseDynamicNumberOfGCThreads", "-XX:+TraceDynamicGCThreads", GCTest.class.getName());
+    String[] baseArgs = {"-XX:+" + gcFlag, "-Xmx10M", "-XX:+PrintGCDetails",  "-XX:+UseDynamicNumberOfGCThreads", "-XX:+TraceDynamicGCThreads", GCTest.class.getName()};
+
+    // Base test with gc and +UseDynamicNumberOfGCThreads:
+    ProcessBuilder pb_enabled = ProcessTools.createJavaProcessBuilder(baseArgs);
+    verifyDynamicNumberOfGCThreads(new OutputAnalyzer(pb_enabled.start()));
+
+    // Ensure it also works on uniprocessors or if user specifies -XX:ParallelGCThreads=1:
+    String[] extraArgs = {"-XX:+UnlockDiagnosticVMOptions", "-XX:+ForceDynamicNumberOfGCThreads", "-XX:ParallelGCThreads=1"};
+    String[] finalArgs = new String[baseArgs.length + extraArgs.length];
+    System.arraycopy(extraArgs, 0, finalArgs, 0,                extraArgs.length);
+    System.arraycopy(baseArgs,  0, finalArgs, extraArgs.length, baseArgs.length);
+    pb_enabled = ProcessTools.createJavaProcessBuilder(finalArgs);
     verifyDynamicNumberOfGCThreads(new OutputAnalyzer(pb_enabled.start()));
   }
 
--- a/hotspot/test/gc/g1/Test2GbHeap.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/Test2GbHeap.java	Wed Jul 05 20:35:10 2017 +0200
@@ -34,8 +34,8 @@
 
 import java.util.ArrayList;
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 
 public class Test2GbHeap {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/gc/g1/TestEagerReclaimHumongousRegions.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestEagerReclaimHumongousRegions.java	Wed Jul 05 20:35:10 2017 +0200
@@ -36,9 +36,9 @@
 import java.util.regex.Matcher;
 import java.util.LinkedList;
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
+import jdk.test.lib.Asserts;
 
 class ReclaimRegionFast {
     public static final int M = 1024*1024;
--- a/hotspot/test/gc/g1/TestEagerReclaimHumongousRegionsClearMarkBits.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestEagerReclaimHumongousRegionsClearMarkBits.java	Wed Jul 05 20:35:10 2017 +0200
@@ -36,8 +36,8 @@
 import java.util.LinkedList;
 import java.util.Random;
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 
 // An object that has a few references to other instances to slow down marking.
 class ObjectWithSomeRefs {
--- a/hotspot/test/gc/g1/TestEagerReclaimHumongousRegionsWithRefs.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestEagerReclaimHumongousRegionsWithRefs.java	Wed Jul 05 20:35:10 2017 +0200
@@ -39,9 +39,9 @@
 import java.util.regex.Matcher;
 import java.util.LinkedList;
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
-import static com.oracle.java.testlibrary.Asserts.*;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
+import static jdk.test.lib.Asserts.*;
 
 class RefHolder {
   Object ref;
--- a/hotspot/test/gc/g1/TestG1TraceEagerReclaimHumongousObjects.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestG1TraceEagerReclaimHumongousObjects.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,8 +32,8 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.ProcessTools;
-import com.oracle.java.testlibrary.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
 import java.util.LinkedList;
 
 public class TestG1TraceEagerReclaimHumongousObjects {
--- a/hotspot/test/gc/g1/TestGCLogMessages.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestGCLogMessages.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,8 +32,8 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.ProcessTools;
-import com.oracle.java.testlibrary.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
 
 public class TestGCLogMessages {
 
--- a/hotspot/test/gc/g1/TestHumongousAllocInitialMark.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestHumongousAllocInitialMark.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class TestHumongousAllocInitialMark {
     // Heap sizes < 224 MB are increased to 224 MB if vm_page_size == 64K to
--- a/hotspot/test/gc/g1/TestHumongousCodeCacheRoots.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestHumongousCodeCacheRoots.java	Wed Jul 05 20:35:10 2017 +0200
@@ -36,7 +36,7 @@
  * @run main TestHumongousCodeCacheRoots
 */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.hotspot.WhiteBox;
 
 import java.util.ArrayList;
--- a/hotspot/test/gc/g1/TestHumongousShrinkHeap.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestHumongousShrinkHeap.java	Wed Jul 05 20:35:10 2017 +0200
@@ -39,7 +39,7 @@
 import java.lang.management.MemoryUsage;
 import java.util.ArrayList;
 import java.util.List;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class TestHumongousShrinkHeap {
 
--- a/hotspot/test/gc/g1/TestLargePageUseForAuxMemory.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestLargePageUseForAuxMemory.java	Wed Jul 05 20:35:10 2017 +0200
@@ -23,19 +23,20 @@
 
 /*
  * @test TestLargePageUseForAuxMemory.java
+ * @summary Test that auxiliary data structures are allocated using large pages if available.
  * @bug 8058354
- * @ignore 8079208
  * @key gc
  * @library /testlibrary /../../test/lib
  * @requires (vm.gc=="G1" | vm.gc=="null")
+ * @build jdk.test.lib.* sun.hotspot.WhiteBox
  * @build TestLargePageUseForAuxMemory
+ * @ignore 8079208
  * @run main ClassFileInstaller sun.hotspot.WhiteBox
  *                              sun.hotspot.WhiteBox$WhiteBoxPermission
- * @summary Test that auxiliary data structures are allocated using large pages if available.
  * @run main/othervm -Xbootclasspath/a:. -XX:+UseG1GC -XX:+WhiteBoxAPI -XX:+IgnoreUnrecognizedVMOptions -XX:+UseLargePages TestLargePageUseForAuxMemory
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.hotspot.WhiteBox;
 
 public class TestLargePageUseForAuxMemory {
--- a/hotspot/test/gc/g1/TestPrintGCDetails.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestPrintGCDetails.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,8 +32,8 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.ProcessTools;
-import com.oracle.java.testlibrary.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
 
 public class TestPrintGCDetails {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/gc/g1/TestPrintRegionRememberedSetInfo.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestPrintRegionRememberedSetInfo.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
  * @author thomas.schatzl@oracle.com
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import java.lang.Thread;
 import java.util.ArrayList;
 import java.util.Arrays;
--- a/hotspot/test/gc/g1/TestShrinkAuxiliaryData.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestShrinkAuxiliaryData.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,11 +21,11 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.ProcessTools;
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.Platform;
+import jdk.test.lib.ProcessTools;
+import jdk.test.lib.Utils;
 import java.io.IOException;
 import java.lang.management.ManagementFactory;
 import java.lang.management.MemoryUsage;
@@ -76,7 +76,6 @@
         printTestInfo(maxCacheSize);
 
         vmOpts.add("-XX:G1ConcRSLogCacheSize=" + hotCardTableSize);
-        vmOpts.addAll(Arrays.asList(Utils.getTestJavaOpts()));
 
         // for 32 bits ObjectAlignmentInBytes is not a option
         if (Platform.is32bit()) {
@@ -98,7 +97,7 @@
 
     private void performTest(List<String> opts) throws Exception {
         ProcessBuilder pb
-                = ProcessTools.createJavaProcessBuilder(
+                = ProcessTools.createJavaProcessBuilder(true,
                         opts.toArray(new String[opts.size()])
                 );
 
--- a/hotspot/test/gc/g1/TestShrinkAuxiliaryData00.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestShrinkAuxiliaryData00.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  * @library /testlibrary /../../test/lib
  * @modules java.base/sun.misc
  *          java.management
- * @build com.oracle.java.testlibrary.* sun.hotspot.WhiteBox
+ * @build jdk.test.lib.* sun.hotspot.WhiteBox
  *        TestShrinkAuxiliaryData TestShrinkAuxiliaryData00
  * @run main ClassFileInstaller sun.hotspot.WhiteBox
  *                              sun.hotspot.WhiteBox$WhiteBoxPermission
--- a/hotspot/test/gc/g1/TestShrinkAuxiliaryData05.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestShrinkAuxiliaryData05.java	Wed Jul 05 20:35:10 2017 +0200
@@ -23,14 +23,14 @@
 
 /**
  * @test TestShrinkAuxiliaryData05
- * @bug 8038423 8061715
+ * @bug 8038423 8061715 8078405
  * @summary Checks that decommitment occurs for JVM with different
  * G1ConcRSLogCacheSize and ObjectAlignmentInBytes options values
  * @requires vm.gc=="G1" | vm.gc=="null"
  * @library /testlibrary /../../test/lib
  * @modules java.base/sun.misc
  *          java.management
- * @build com.oracle.java.testlibrary.* sun.hotspot.WhiteBox
+ * @build jdk.test.lib.* sun.hotspot.WhiteBox
  *        TestShrinkAuxiliaryData TestShrinkAuxiliaryData05
  * @run main ClassFileInstaller sun.hotspot.WhiteBox
  *                              sun.hotspot.WhiteBox$WhiteBoxPermission
--- a/hotspot/test/gc/g1/TestShrinkAuxiliaryData10.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestShrinkAuxiliaryData10.java	Wed Jul 05 20:35:10 2017 +0200
@@ -23,14 +23,14 @@
 
 /**
  * @test TestShrinkAuxiliaryData10
- * @bug 8038423 8061715
+ * @bug 8038423 8061715 8078405
  * @summary Checks that decommitment occurs for JVM with different
  * G1ConcRSLogCacheSize and ObjectAlignmentInBytes options values
  * @requires vm.gc=="G1" | vm.gc=="null"
  * @library /testlibrary /../../test/lib
  * @modules java.base/sun.misc
  *          java.management
- * @build com.oracle.java.testlibrary.* sun.hotspot.WhiteBox
+ * @build jdk.test.lib.* sun.hotspot.WhiteBox
  * @build TestShrinkAuxiliaryData TestShrinkAuxiliaryData10
  * @run main ClassFileInstaller sun.hotspot.WhiteBox
  *                              sun.hotspot.WhiteBox$WhiteBoxPermission
--- a/hotspot/test/gc/g1/TestShrinkAuxiliaryData15.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestShrinkAuxiliaryData15.java	Wed Jul 05 20:35:10 2017 +0200
@@ -23,14 +23,14 @@
 
 /**
  * @test TestShrinkAuxiliaryData15
- * @bug 8038423 8061715
+ * @bug 8038423 8061715 8078405
  * @summary Checks that decommitment occurs for JVM with different
  * G1ConcRSLogCacheSize and ObjectAlignmentInBytes options values
  * @requires vm.gc=="G1" | vm.gc=="null"
  * @library /testlibrary /../../test/lib
  * @modules java.base/sun.misc
  *          java.management
- * @build com.oracle.java.testlibrary.* sun.hotspot.WhiteBox
+ * @build jdk.test.lib.* sun.hotspot.WhiteBox
  * @build TestShrinkAuxiliaryData TestShrinkAuxiliaryData15
  * @run main ClassFileInstaller sun.hotspot.WhiteBox
  *                              sun.hotspot.WhiteBox$WhiteBoxPermission
--- a/hotspot/test/gc/g1/TestShrinkAuxiliaryData20.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestShrinkAuxiliaryData20.java	Wed Jul 05 20:35:10 2017 +0200
@@ -23,14 +23,14 @@
 
 /**
  * @test TestShrinkAuxiliaryData20
- * @bug 8038423 8061715
+ * @bug 8038423 8061715 8078405
  * @summary Checks that decommitment occurs for JVM with different
  * G1ConcRSLogCacheSize and ObjectAlignmentInBytes options values
  * @requires vm.gc=="G1" | vm.gc=="null"
  * @library /testlibrary /../../test/lib
  * @modules java.base/sun.misc
   *          java.management
- * @build com.oracle.java.testlibrary.* sun.hotspot.WhiteBox
+ * @build jdk.test.lib.* sun.hotspot.WhiteBox
  * @build TestShrinkAuxiliaryData TestShrinkAuxiliaryData20
  * @run main ClassFileInstaller sun.hotspot.WhiteBox
  *                              sun.hotspot.WhiteBox$WhiteBoxPermission
--- a/hotspot/test/gc/g1/TestShrinkAuxiliaryData25.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestShrinkAuxiliaryData25.java	Wed Jul 05 20:35:10 2017 +0200
@@ -23,14 +23,14 @@
 
 /**
  * @test TestShrinkAuxiliaryData25
- * @bug 8038423 8061715
+ * @bug 8038423 8061715 8078405
  * @summary Checks that decommitment occurs for JVM with different
  * G1ConcRSLogCacheSize and ObjectAlignmentInBytes options values
  * @requires vm.gc=="G1" | vm.gc=="null"
  * @library /testlibrary /../../test/lib
  * @modules java.base/sun.misc
  *          java.management
- * @build com.oracle.java.testlibrary.* sun.hotspot.WhiteBox
+ * @build jdk.test.lib.* sun.hotspot.WhiteBox
  * @build TestShrinkAuxiliaryData TestShrinkAuxiliaryData25
  * @run main ClassFileInstaller sun.hotspot.WhiteBox
  *                              sun.hotspot.WhiteBox$WhiteBoxPermission
--- a/hotspot/test/gc/g1/TestShrinkAuxiliaryData30.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestShrinkAuxiliaryData30.java	Wed Jul 05 20:35:10 2017 +0200
@@ -23,14 +23,14 @@
 
 /**
  * @test TestShrinkAuxiliaryData30
- * @bug 8038423 8061715
+ * @bug 8038423 8061715 8078405
  * @summary Checks that decommitment occurs for JVM with different
  * G1ConcRSLogCacheSize and ObjectAlignmentInBytes options values
  * @requires vm.gc=="G1" | vm.gc=="null"
  * @library /testlibrary /../../test/lib
  * @modules java.base/sun.misc
  *          java.management
- * @build com.oracle.java.testlibrary.* sun.hotspot.WhiteBox
+ * @build jdk.test.lib.* sun.hotspot.WhiteBox
  * @build TestShrinkAuxiliaryData TestShrinkAuxiliaryData30
  * @run main ClassFileInstaller sun.hotspot.WhiteBox
  *                              sun.hotspot.WhiteBox$WhiteBoxPermission
--- a/hotspot/test/gc/g1/TestShrinkDefragmentedHeap.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestShrinkDefragmentedHeap.java	Wed Jul 05 20:35:10 2017 +0200
@@ -39,9 +39,9 @@
 import java.lang.management.MemoryUsage;
 import java.util.ArrayList;
 import java.util.List;
-import static com.oracle.java.testlibrary.Asserts.*;
-import com.oracle.java.testlibrary.ProcessTools;
-import com.oracle.java.testlibrary.OutputAnalyzer;
+import static jdk.test.lib.Asserts.*;
+import jdk.test.lib.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
 import com.sun.management.HotSpotDiagnosticMXBean;
 
 public class TestShrinkDefragmentedHeap {
--- a/hotspot/test/gc/g1/TestStringDeduplicationTools.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestStringDeduplicationTools.java	Wed Jul 05 20:35:10 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
@@ -29,7 +29,7 @@
 import java.lang.reflect.*;
 import java.security.*;
 import java.util.*;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.*;
 
 class TestStringDeduplicationTools {
--- a/hotspot/test/gc/g1/TestStringSymbolTableStats.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestStringSymbolTableStats.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,8 +31,8 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.ProcessTools;
-import com.oracle.java.testlibrary.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
 
 public class TestStringSymbolTableStats {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/gc/g1/TestSummarizeRSetStatsPerRegion.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestSummarizeRSetStatsPerRegion.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  * @run main TestSummarizeRSetStatsPerRegion
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import java.lang.Thread;
 import java.util.ArrayList;
 import java.util.Arrays;
--- a/hotspot/test/gc/g1/TestSummarizeRSetStatsThreads.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestSummarizeRSetStatsThreads.java	Wed Jul 05 20:35:10 2017 +0200
@@ -35,8 +35,8 @@
 import java.util.regex.Matcher;
 import java.util.regex.Pattern;
 
-import com.oracle.java.testlibrary.ProcessTools;
-import com.oracle.java.testlibrary.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
 
 public class TestSummarizeRSetStatsThreads {
 
--- a/hotspot/test/gc/g1/TestSummarizeRSetStatsTools.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/g1/TestSummarizeRSetStatsTools.java	Wed Jul 05 20:35:10 2017 +0200
@@ -28,7 +28,7 @@
 import com.sun.management.HotSpotDiagnosticMXBean;
 import com.sun.management.VMOption;
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import java.lang.management.ManagementFactory;
 import java.util.ArrayList;
 import java.util.Arrays;
--- a/hotspot/test/gc/logging/TestGCId.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/logging/TestGCId.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,8 +31,8 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.ProcessTools;
-import com.oracle.java.testlibrary.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
 
 public class TestGCId {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/gc/metaspace/CompressedClassSpaceSizeInJmapHeap.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/metaspace/CompressedClassSpaceSizeInJmapHeap.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  * @run main/othervm -XX:+IgnoreUnrecognizedVMOptions -XX:CompressedClassSpaceSize=50m CompressedClassSpaceSizeInJmapHeap
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import java.nio.file.*;
 import java.io.File;
 import java.nio.charset.Charset;
--- a/hotspot/test/gc/metaspace/TestCapacityUntilGCWrapAround.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/metaspace/TestCapacityUntilGCWrapAround.java	Wed Jul 05 20:35:10 2017 +0200
@@ -36,8 +36,8 @@
 
 import sun.hotspot.WhiteBox;
 
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.Platform;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.Platform;
 
 public class TestCapacityUntilGCWrapAround {
     private static long MB = 1024 * 1024;
--- a/hotspot/test/gc/metaspace/TestMetaspaceMemoryPool.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/metaspace/TestMetaspaceMemoryPool.java	Wed Jul 05 20:35:10 2017 +0200
@@ -23,8 +23,8 @@
 
 import java.util.List;
 import java.lang.management.*;
-import com.oracle.java.testlibrary.*;
-import static com.oracle.java.testlibrary.Asserts.*;
+import jdk.test.lib.*;
+import static jdk.test.lib.Asserts.*;
 
 /* @test TestMetaspaceMemoryPool
  * @bug 8000754
--- a/hotspot/test/gc/metaspace/TestMetaspacePerfCounters.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/metaspace/TestMetaspacePerfCounters.java	Wed Jul 05 20:35:10 2017 +0200
@@ -24,8 +24,8 @@
 import java.util.List;
 import java.util.ArrayList;
 
-import com.oracle.java.testlibrary.*;
-import static com.oracle.java.testlibrary.Asserts.*;
+import jdk.test.lib.*;
+import static jdk.test.lib.Asserts.*;
 
 /* @test TestMetaspacePerfCounters
  * @bug 8014659
--- a/hotspot/test/gc/metaspace/TestMetaspaceSizeFlags.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/metaspace/TestMetaspaceSizeFlags.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,9 +21,9 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 
 /*
  * @test TestMetaspaceSizeFlags
--- a/hotspot/test/gc/metaspace/TestPerfCountersAndMemoryPools.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/metaspace/TestPerfCountersAndMemoryPools.java	Wed Jul 05 20:35:10 2017 +0200
@@ -24,8 +24,8 @@
 import java.util.List;
 import java.lang.management.*;
 
-import com.oracle.java.testlibrary.*;
-import static com.oracle.java.testlibrary.Asserts.*;
+import jdk.test.lib.*;
+import static jdk.test.lib.Asserts.*;
 
 /* @test TestPerfCountersAndMemoryPools
  * @bug 8023476
--- a/hotspot/test/gc/parallelScavenge/AdaptiveGCBoundary.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/parallelScavenge/AdaptiveGCBoundary.java	Wed Jul 05 20:35:10 2017 +0200
@@ -34,7 +34,7 @@
  * @author jon.masamitsu@oracle.com
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class AdaptiveGCBoundary {
   public static void main(String args[]) throws Exception {
--- a/hotspot/test/gc/parallelScavenge/TestDynShrinkHeap.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/parallelScavenge/TestDynShrinkHeap.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,11 +29,11 @@
  * @library /testlibrary
  * @run main/othervm -XX:+UseAdaptiveSizePolicyWithSystemGC -XX:+UseParallelGC -XX:MinHeapFreeRatio=0 -XX:MaxHeapFreeRatio=100 -Xmx1g -verbose:gc TestDynShrinkHeap
  */
-import com.oracle.java.testlibrary.DynamicVMOption;
+import jdk.test.lib.DynamicVMOption;
 import java.lang.management.ManagementFactory;
 import java.lang.management.MemoryUsage;
 import java.util.ArrayList;
-import static com.oracle.java.testlibrary.Asserts.assertLessThan;
+import static jdk.test.lib.Asserts.assertLessThan;
 import com.sun.management.HotSpotDiagnosticMXBean;
 
 public class TestDynShrinkHeap {
--- a/hotspot/test/gc/startup_warnings/TestCMS.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/startup_warnings/TestCMS.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,8 +31,8 @@
 *          java.management
 */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 
 
 public class TestCMS {
--- a/hotspot/test/gc/startup_warnings/TestDefNewCMS.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/startup_warnings/TestDefNewCMS.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,8 +31,8 @@
 *          java.management
 */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 
 public class TestDefNewCMS {
 
--- a/hotspot/test/gc/startup_warnings/TestDefaultMaxRAMFraction.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/startup_warnings/TestDefaultMaxRAMFraction.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,8 +31,8 @@
 *          java.management
 */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 
 public class TestDefaultMaxRAMFraction {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/gc/startup_warnings/TestG1.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/startup_warnings/TestG1.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,8 +31,8 @@
 *          java.management
 */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 
 public class TestG1 {
 
--- a/hotspot/test/gc/startup_warnings/TestNoParNew.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/startup_warnings/TestNoParNew.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,8 +31,8 @@
 *          java.management
 */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 
 
 public class TestNoParNew {
--- a/hotspot/test/gc/startup_warnings/TestParNewCMS.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/startup_warnings/TestParNewCMS.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,8 +31,8 @@
 *          java.management
 */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 
 
 public class TestParNewCMS {
--- a/hotspot/test/gc/startup_warnings/TestParNewSerialOld.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/startup_warnings/TestParNewSerialOld.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,8 +31,8 @@
 *          java.management
 */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 
 
 public class TestParNewSerialOld {
--- a/hotspot/test/gc/startup_warnings/TestParallelGC.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/startup_warnings/TestParallelGC.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,8 +31,8 @@
 *          java.management
 */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 
 
 public class TestParallelGC {
--- a/hotspot/test/gc/startup_warnings/TestParallelScavengeSerialOld.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/startup_warnings/TestParallelScavengeSerialOld.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,8 +31,8 @@
 *          java.management
 */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 
 
 public class TestParallelScavengeSerialOld {
--- a/hotspot/test/gc/startup_warnings/TestSerialGC.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/startup_warnings/TestSerialGC.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,8 +31,8 @@
 *          java.management
 */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 
 
 public class TestSerialGC {
--- a/hotspot/test/gc/survivorAlignment/SurvivorAlignmentTestMain.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/survivorAlignment/SurvivorAlignmentTestMain.java	Wed Jul 05 20:35:10 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
@@ -28,7 +28,7 @@
 import java.util.regex.Matcher;
 import java.util.regex.Pattern;
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 import com.sun.management.ThreadMXBean;
 import sun.hotspot.WhiteBox;
 import sun.misc.Unsafe;
--- a/hotspot/test/gc/whitebox/TestConcMarkCycleWB.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/whitebox/TestConcMarkCycleWB.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,14 +30,14 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build ClassFileInstaller com.oracle.java.testlibrary.* sun.hotspot.WhiteBox TestConcMarkCycleWB
+ * @build ClassFileInstaller jdk.test.lib.* sun.hotspot.WhiteBox TestConcMarkCycleWB
  * @run main ClassFileInstaller sun.hotspot.WhiteBox
  *                              sun.hotspot.WhiteBox$WhiteBoxPermission
  * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI -XX:+UseG1GC TestConcMarkCycleWB
  * @summary Verifies that ConcurrentMarking-related WB works properly
  */
-import static com.oracle.java.testlibrary.Asserts.assertFalse;
-import static com.oracle.java.testlibrary.Asserts.assertTrue;
+import static jdk.test.lib.Asserts.assertFalse;
+import static jdk.test.lib.Asserts.assertTrue;
 import sun.hotspot.WhiteBox;
 
 public class TestConcMarkCycleWB {
--- a/hotspot/test/gc/whitebox/TestWBGC.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/gc/whitebox/TestWBGC.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  * @run main ClassFileInstaller sun.hotspot.WhiteBox
  * @run driver TestWBGC
  */
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.hotspot.WhiteBox;
 
 public class TestWBGC {
--- a/hotspot/test/runtime/BadObjectClass/BootstrapRedefine.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/BadObjectClass/BootstrapRedefine.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  * @run main BootstrapRedefine
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class BootstrapRedefine {
 
--- a/hotspot/test/runtime/CDSCompressedKPtrs/CDSCompressedKPtrs.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CDSCompressedKPtrs/CDSCompressedKPtrs.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  * @run main CDSCompressedKPtrs
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class CDSCompressedKPtrs {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/runtime/CDSCompressedKPtrs/CDSCompressedKPtrsError.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CDSCompressedKPtrs/CDSCompressedKPtrsError.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  * @run main CDSCompressedKPtrsError
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class CDSCompressedKPtrsError {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/runtime/CDSCompressedKPtrs/XShareAuto.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CDSCompressedKPtrs/XShareAuto.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  * @run main XShareAuto
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class XShareAuto {
     public static void main(String[] args) throws Exception {
--- a/hotspot/test/runtime/ClassFile/JsrRewriting.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/ClassFile/JsrRewriting.java	Wed Jul 05 20:35:10 2017 +0200
@@ -40,7 +40,7 @@
  * @run main JsrRewriting
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import java.io.File;
 
 public class JsrRewriting {
--- a/hotspot/test/runtime/ClassFile/OomWhileParsingRepeatedJsr.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/ClassFile/OomWhileParsingRepeatedJsr.java	Wed Jul 05 20:35:10 2017 +0200
@@ -40,7 +40,7 @@
  * @run main OomWhileParsingRepeatedJsr
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 
 public class OomWhileParsingRepeatedJsr {
--- a/hotspot/test/runtime/ClassFile/UnsupportedClassFileVersion.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/ClassFile/UnsupportedClassFileVersion.java	Wed Jul 05 20:35:10 2017 +0200
@@ -36,7 +36,7 @@
 import jdk.internal.org.objectweb.asm.ClassWriter;
 import jdk.internal.org.objectweb.asm.MethodVisitor;
 import jdk.internal.org.objectweb.asm.Opcodes;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class UnsupportedClassFileVersion implements Opcodes {
     public static void main(String... args) throws Exception {
--- a/hotspot/test/runtime/CommandLine/BooleanFlagWithInvalidValue.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CommandLine/BooleanFlagWithInvalidValue.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class BooleanFlagWithInvalidValue {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/runtime/CommandLine/CompilerConfigFileWarning.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CommandLine/CompilerConfigFileWarning.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  */
 
 import java.io.PrintWriter;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class CompilerConfigFileWarning {
     public static void main(String[] args) throws Exception {
--- a/hotspot/test/runtime/CommandLine/ConfigFileParsing.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CommandLine/ConfigFileParsing.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  */
 
 import java.io.PrintWriter;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class ConfigFileParsing {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/runtime/CommandLine/ConfigFileWarning.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CommandLine/ConfigFileWarning.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  */
 
 import java.io.PrintWriter;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class ConfigFileWarning {
     public static void main(String[] args) throws Exception {
--- a/hotspot/test/runtime/CommandLine/FlagWithInvalidValue.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CommandLine/FlagWithInvalidValue.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class FlagWithInvalidValue {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/runtime/CommandLine/NonBooleanFlagWithInvalidBooleanPrefix.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CommandLine/NonBooleanFlagWithInvalidBooleanPrefix.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class NonBooleanFlagWithInvalidBooleanPrefix {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/runtime/CommandLine/ObsoleteFlagErrorMessage.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CommandLine/ObsoleteFlagErrorMessage.java	Wed Jul 05 20:35:10 2017 +0200
@@ -28,7 +28,7 @@
  * @library /testlibrary
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class ObsoleteFlagErrorMessage {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/runtime/CommandLine/TestHexArguments.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CommandLine/TestHexArguments.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  */
 
 import java.io.File;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class TestHexArguments {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/CommandLine/TestNullTerminatedFlags.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CommandLine/TestNullTerminatedFlags.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 /*
  * @test TestNullTerminatedFlags
--- a/hotspot/test/runtime/CommandLine/TestVMOptions.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CommandLine/TestVMOptions.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  * @run main TestVMOptions
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import java.io.File;
 
 public class TestVMOptions {
--- a/hotspot/test/runtime/CommandLine/TraceExceptionsTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CommandLine/TraceExceptionsTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class TraceExceptionsTest {
     public static void main(String[] args) throws Exception {
--- a/hotspot/test/runtime/CommandLine/UnrecognizedVMOption.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CommandLine/UnrecognizedVMOption.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class UnrecognizedVMOption {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/runtime/CommandLine/VMOptionWarning.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CommandLine/VMOptionWarning.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class VMOptionWarning {
     public static void main(String[] args) throws Exception {
--- a/hotspot/test/runtime/CompressedOops/CompressedClassPointers.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CompressedOops/CompressedClassPointers.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class CompressedClassPointers {
 
--- a/hotspot/test/runtime/CompressedOops/CompressedClassSpaceSize.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CompressedOops/CompressedClassSpaceSize.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  * @run main CompressedClassSpaceSize
  */
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class CompressedClassSpaceSize {
 
--- a/hotspot/test/runtime/CompressedOops/CompressedKlassPointerAndOops.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CompressedOops/CompressedKlassPointerAndOops.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class CompressedKlassPointerAndOops {
 
--- a/hotspot/test/runtime/CompressedOops/ObjectAlignment.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CompressedOops/ObjectAlignment.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  * @run main ObjectAlignment
  */
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class ObjectAlignment {
 
--- a/hotspot/test/runtime/CompressedOops/UseCompressedOops.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/CompressedOops/UseCompressedOops.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  */
 import java.util.ArrayList;
 import java.util.Collections;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class UseCompressedOops {
 
--- a/hotspot/test/runtime/EnclosingMethodAttr/EnclMethodAttr.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/EnclosingMethodAttr/EnclMethodAttr.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  */
 
 import java.io.File;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class EnclMethodAttr {
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/runtime/ErrorHandling/CreateCoredumpOnCrash.java	Wed Jul 05 20:35:10 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.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/*
+ * @test
+ * @library /testlibrary
+ * @modules java.base/sun.misc
+ *          java.compiler
+ *          java.management
+ *          jdk.jvmstat/sun.jvmstat.monitor
+ * @build jdk.test.lib.*
+ * @run driver CreateCoredumpOnCrash
+ */
+
+import jdk.test.lib.*;
+import sun.misc.Unsafe;
+
+public class CreateCoredumpOnCrash {
+    private static class Crasher {
+        public static void main(String[] args) {
+            Utils.getUnsafe().getInt(0);
+        }
+    }
+
+    public static void main(String[] args) throws Exception {
+        runTest("-XX:-CreateCoredumpOnCrash").shouldContain("CreateCoredumpOnCrash turned off, no core file dumped");
+
+        if (Platform.isWindows()) {
+            runTest("-XX:+CreateCoredumpOnCrash").shouldContain("Core dump will be written. Default location");
+
+            // The old CreateMinidumpOnCrash option should still work
+            runTest("-XX:+CreateMinidumpOnCrash").shouldContain("Core dump will be written. Default location");
+            runTest("-XX:-CreateMinidumpOnCrash").shouldContain("CreateCoredumpOnCrash turned off, no core file dumped");
+
+            if (Platform.isDebugBuild()) {
+                // Make sure we create dumps on Windows debug builds by default
+                runTest("-Ddummyopt=false").shouldContain("Core dump will be written. Default location");
+            }
+        } else {
+            runTest("-XX:+CreateCoredumpOnCrash").shouldNotContain("CreateCoredumpOnCrash turned off, no core file dumped");
+        }
+
+    }
+    public static OutputAnalyzer runTest(String option) throws Exception {
+        return new OutputAnalyzer(
+            ProcessTools.createJavaProcessBuilder(
+            "-Xmx64m", "-XX:-TransmitErrorReport", option, Crasher.class.getName())
+            .start());
+    }
+}
--- a/hotspot/test/runtime/ErrorHandling/ProblematicFrameTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/ErrorHandling/ProblematicFrameTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,14 +30,14 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.*
+ * @build jdk.test.lib.*
  * @run driver ProblematicFrameTest
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 import sun.misc.Unsafe;
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Utils;
 
 public class ProblematicFrameTest {
     private static class Crasher {
--- a/hotspot/test/runtime/ErrorHandling/SafeFetchInErrorHandlingTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/ErrorHandling/SafeFetchInErrorHandlingTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -27,9 +27,9 @@
 import java.io.InputStreamReader;
 import java.util.regex.Pattern;
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.Platform;
+import jdk.test.lib.ProcessTools;
 
 /*
  * @test
--- a/hotspot/test/runtime/ErrorHandling/SecondaryErrorTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/ErrorHandling/SecondaryErrorTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,9 +38,9 @@
 import java.io.InputStreamReader;
 import java.util.regex.Pattern;
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.Platform;
+import jdk.test.lib.ProcessTools;
 
 public class SecondaryErrorTest {
 
--- a/hotspot/test/runtime/LoadClass/LoadClassNegative.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/LoadClass/LoadClassNegative.java	Wed Jul 05 20:35:10 2017 +0200
@@ -35,7 +35,7 @@
  */
 
 import java.io.File;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class LoadClassNegative {
 
--- a/hotspot/test/runtime/LocalVariableTable/TestLVT.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/LocalVariableTable/TestLVT.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  * @run main TestLVT
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import java.util.*;
 
 public class TestLVT {
--- a/hotspot/test/runtime/NMT/AutoshutdownNMT.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/AutoshutdownNMT.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class AutoshutdownNMT {
 
--- a/hotspot/test/runtime/NMT/BaselineWithParameter.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/BaselineWithParameter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  * @run main/othervm -XX:NativeMemoryTracking=detail BaselineWithParameter
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class BaselineWithParameter {
 
--- a/hotspot/test/runtime/NMT/ChangeTrackingLevel.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/ChangeTrackingLevel.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
  * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI -XX:NativeMemoryTracking=detail ChangeTrackingLevel
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.hotspot.WhiteBox;
 
 public class ChangeTrackingLevel {
--- a/hotspot/test/runtime/NMT/CommandLineDetail.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/CommandLineDetail.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class CommandLineDetail {
 
--- a/hotspot/test/runtime/NMT/CommandLineEmptyArgument.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/CommandLineEmptyArgument.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class CommandLineEmptyArgument {
 
--- a/hotspot/test/runtime/NMT/CommandLineInvalidArgument.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/CommandLineInvalidArgument.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class CommandLineInvalidArgument {
 
--- a/hotspot/test/runtime/NMT/CommandLineSummary.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/CommandLineSummary.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class CommandLineSummary {
 
--- a/hotspot/test/runtime/NMT/CommandLineTurnOffNMT.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/CommandLineTurnOffNMT.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class CommandLineTurnOffNMT {
 
--- a/hotspot/test/runtime/NMT/JcmdBaselineDetail.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/JcmdBaselineDetail.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  * @run main/othervm -XX:NativeMemoryTracking=detail JcmdBaselineDetail
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class JcmdBaselineDetail {
 
--- a/hotspot/test/runtime/NMT/JcmdDetailDiff.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/JcmdDetailDiff.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
  * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI -XX:NativeMemoryTracking=detail JcmdDetailDiff
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 import sun.hotspot.WhiteBox;
 
--- a/hotspot/test/runtime/NMT/JcmdScale.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/JcmdScale.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  * @run main/othervm -XX:NativeMemoryTracking=summary JcmdScale
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class JcmdScale {
 
--- a/hotspot/test/runtime/NMT/JcmdScaleDetail.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/JcmdScaleDetail.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  * @run main/othervm -XX:NativeMemoryTracking=detail JcmdScaleDetail
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class JcmdScaleDetail {
 
--- a/hotspot/test/runtime/NMT/JcmdSummaryDiff.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/JcmdSummaryDiff.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
  * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI -XX:NativeMemoryTracking=summary JcmdSummaryDiff
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 import sun.hotspot.WhiteBox;
 
--- a/hotspot/test/runtime/NMT/JcmdWithNMTDisabled.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/JcmdWithNMTDisabled.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  * @run main JcmdWithNMTDisabled 1
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class JcmdWithNMTDisabled {
   static ProcessBuilder pb = new ProcessBuilder();
--- a/hotspot/test/runtime/NMT/MallocRoundingReportTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/MallocRoundingReportTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -34,7 +34,7 @@
  *
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 import sun.hotspot.WhiteBox;
 
--- a/hotspot/test/runtime/NMT/MallocSiteHashOverflow.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/MallocSiteHashOverflow.java	Wed Jul 05 20:35:10 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
@@ -32,7 +32,7 @@
  * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI -XX:NativeMemoryTracking=detail MallocSiteHashOverflow
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.hotspot.WhiteBox;
 
 public class MallocSiteHashOverflow {
--- a/hotspot/test/runtime/NMT/MallocStressTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/MallocStressTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,7 +38,7 @@
 import java.util.ArrayList;
 import java.util.List;
 import java.util.Random;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.hotspot.WhiteBox;
 
 public class MallocStressTest {
--- a/hotspot/test/runtime/NMT/MallocTestType.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/MallocTestType.java	Wed Jul 05 20:35:10 2017 +0200
@@ -34,7 +34,7 @@
  * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI -XX:NativeMemoryTracking=detail MallocTestType
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.hotspot.WhiteBox;
 
 public class MallocTestType {
--- a/hotspot/test/runtime/NMT/MallocTrackingVerify.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/MallocTrackingVerify.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,7 +38,7 @@
 import java.util.ArrayList;
 import java.util.Random;
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 import sun.hotspot.WhiteBox;
 
--- a/hotspot/test/runtime/NMT/NMTWithCDS.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/NMTWithCDS.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  * @run main NMTWithCDS
  */
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class NMTWithCDS {
 
--- a/hotspot/test/runtime/NMT/PrintNMTStatistics.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/PrintNMTStatistics.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,7 +29,7 @@
  * @library /testlibrary
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class PrintNMTStatistics {
 
--- a/hotspot/test/runtime/NMT/PrintNMTStatisticsWithNMTDisabled.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/PrintNMTStatisticsWithNMTDisabled.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class PrintNMTStatisticsWithNMTDisabled {
 
--- a/hotspot/test/runtime/NMT/ReleaseNoCommit.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/ReleaseNoCommit.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,9 +33,9 @@
  * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI -XX:NativeMemoryTracking=summary ReleaseNoCommit
  */
 
-import com.oracle.java.testlibrary.JDKToolFinder;
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.JDKToolFinder;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 
 import sun.hotspot.WhiteBox;
 
--- a/hotspot/test/runtime/NMT/ShutdownTwice.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/ShutdownTwice.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  * @run main/othervm -XX:NativeMemoryTracking=detail ShutdownTwice
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class ShutdownTwice {
 
--- a/hotspot/test/runtime/NMT/SummaryAfterShutdown.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/SummaryAfterShutdown.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  * @run main/othervm -XX:NativeMemoryTracking=detail SummaryAfterShutdown
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class SummaryAfterShutdown {
 
--- a/hotspot/test/runtime/NMT/SummarySanityCheck.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/SummarySanityCheck.java	Wed Jul 05 20:35:10 2017 +0200
@@ -34,7 +34,7 @@
  * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:NativeMemoryTracking=summary -XX:+WhiteBoxAPI SummarySanityCheck
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 import java.util.regex.Matcher;
 import java.util.regex.Pattern;
--- a/hotspot/test/runtime/NMT/ThreadedMallocTestType.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/ThreadedMallocTestType.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
  * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI -XX:NativeMemoryTracking=detail ThreadedMallocTestType
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.hotspot.WhiteBox;
 
 public class ThreadedMallocTestType {
--- a/hotspot/test/runtime/NMT/ThreadedVirtualAllocTestType.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/ThreadedVirtualAllocTestType.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
  * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI -XX:NativeMemoryTracking=detail ThreadedVirtualAllocTestType
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.hotspot.WhiteBox;
 
 public class ThreadedVirtualAllocTestType {
--- a/hotspot/test/runtime/NMT/VirtualAllocCommitUncommitRecommit.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/VirtualAllocCommitUncommitRecommit.java	Wed Jul 05 20:35:10 2017 +0200
@@ -34,7 +34,7 @@
  *
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 import sun.hotspot.WhiteBox;
 
--- a/hotspot/test/runtime/NMT/VirtualAllocTestType.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/NMT/VirtualAllocTestType.java	Wed Jul 05 20:35:10 2017 +0200
@@ -34,7 +34,7 @@
  * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI -XX:NativeMemoryTracking=detail VirtualAllocTestType
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.hotspot.WhiteBox;
 
 public class VirtualAllocTestType {
--- a/hotspot/test/runtime/PerfMemDestroy/PerfMemDestroy.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/PerfMemDestroy/PerfMemDestroy.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
 
 import java.io.File;
 import java.util.Map;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class PerfMemDestroy {
     public static void main(String args[]) throws Throwable {
--- a/hotspot/test/runtime/RedefineObject/TestRedefineObject.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/RedefineObject/TestRedefineObject.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,7 +21,7 @@
  * questions.
  */
 import java.io.PrintWriter;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 /*
  * Test to redefine java/lang/Object and verify that it doesn't crash on vtable
--- a/hotspot/test/runtime/RedefineTests/RedefineAnnotations.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/RedefineTests/RedefineAnnotations.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  * @run main/othervm -javaagent:redefineagent.jar RedefineAnnotations
  */
 
-import static com.oracle.java.testlibrary.Asserts.assertTrue;
+import static jdk.test.lib.Asserts.assertTrue;
 import java.io.FileNotFoundException;
 import java.io.PrintWriter;
 import java.lang.NoSuchFieldException;
--- a/hotspot/test/runtime/Safepoint/AssertSafepointCheckConsistency1.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Safepoint/AssertSafepointCheckConsistency1.java	Wed Jul 05 20:35:10 2017 +0200
@@ -34,7 +34,7 @@
  * @run main AssertSafepointCheckConsistency1
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 import sun.hotspot.WhiteBox;
 
--- a/hotspot/test/runtime/Safepoint/AssertSafepointCheckConsistency2.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Safepoint/AssertSafepointCheckConsistency2.java	Wed Jul 05 20:35:10 2017 +0200
@@ -34,7 +34,7 @@
  * @run main AssertSafepointCheckConsistency2
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 import sun.hotspot.WhiteBox;
 
--- a/hotspot/test/runtime/Safepoint/AssertSafepointCheckConsistency3.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Safepoint/AssertSafepointCheckConsistency3.java	Wed Jul 05 20:35:10 2017 +0200
@@ -34,7 +34,7 @@
  * @run main AssertSafepointCheckConsistency3
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 import sun.hotspot.WhiteBox;
 
--- a/hotspot/test/runtime/Safepoint/AssertSafepointCheckConsistency4.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Safepoint/AssertSafepointCheckConsistency4.java	Wed Jul 05 20:35:10 2017 +0200
@@ -34,7 +34,7 @@
  * @run main AssertSafepointCheckConsistency4
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 import sun.hotspot.WhiteBox;
 
--- a/hotspot/test/runtime/SharedArchiveFile/ArchiveDoesNotExist.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/SharedArchiveFile/ArchiveDoesNotExist.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
  * @run main ArchiveDoesNotExist
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import java.io.File;
 
 public class ArchiveDoesNotExist {
--- a/hotspot/test/runtime/SharedArchiveFile/CdsDifferentObjectAlignment.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/SharedArchiveFile/CdsDifferentObjectAlignment.java	Wed Jul 05 20:35:10 2017 +0200
@@ -34,7 +34,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class CdsDifferentObjectAlignment {
     public static void main(String[] args) throws Exception {
--- a/hotspot/test/runtime/SharedArchiveFile/CdsSameObjectAlignment.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/SharedArchiveFile/CdsSameObjectAlignment.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class CdsSameObjectAlignment {
     public static void main(String[] args) throws Exception {
--- a/hotspot/test/runtime/SharedArchiveFile/DefaultUseWithClient.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/SharedArchiveFile/DefaultUseWithClient.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  * @bug 8032224
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import java.io.File;
 
 public class DefaultUseWithClient {
--- a/hotspot/test/runtime/SharedArchiveFile/DumpSymbolAndStringTable.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/SharedArchiveFile/DumpSymbolAndStringTable.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  * @run main/othervm -XX:+UnlockDiagnosticVMOptions DumpSymbolAndStringTable
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class DumpSymbolAndStringTable {
     public static void main(String[] args) throws Exception {
--- a/hotspot/test/runtime/SharedArchiveFile/LimitSharedSizes.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/SharedArchiveFile/LimitSharedSizes.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,7 +29,7 @@
  * @run main LimitSharedSizes
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class LimitSharedSizes {
     static enum Region {
--- a/hotspot/test/runtime/SharedArchiveFile/MaxMetaspaceSize.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/SharedArchiveFile/MaxMetaspaceSize.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class MaxMetaspaceSize {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/runtime/SharedArchiveFile/PrintSharedArchiveAndExit.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/SharedArchiveFile/PrintSharedArchiveAndExit.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class PrintSharedArchiveAndExit {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/runtime/SharedArchiveFile/SharedArchiveFile.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/SharedArchiveFile/SharedArchiveFile.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class SharedArchiveFile {
   public static void main(String[] args) throws Exception {
--- a/hotspot/test/runtime/SharedArchiveFile/SharedBaseAddress.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/SharedArchiveFile/SharedBaseAddress.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  * @run main SharedBaseAddress
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class SharedBaseAddress {
 
--- a/hotspot/test/runtime/SharedArchiveFile/SharedSymbolTableBucketSize.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/SharedArchiveFile/SharedSymbolTableBucketSize.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class SharedSymbolTableBucketSize {
     public static void main(String[] args) throws Exception {
--- a/hotspot/test/runtime/SharedArchiveFile/SpaceUtilizationCheck.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/SharedArchiveFile/SpaceUtilizationCheck.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  * @run main SpaceUtilizationCheck
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 import java.util.regex.Pattern;
 import java.util.regex.Matcher;
--- a/hotspot/test/runtime/Thread/Fibonacci.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Thread/Fibonacci.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  * @run main Fibonacci 15
  */
 
-import com.oracle.java.testlibrary.Asserts;
+import jdk.test.lib.Asserts;
 
 public class Fibonacci extends Thread {
     private int index;
--- a/hotspot/test/runtime/Thread/TestThreadDumpMonitorContention.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Thread/TestThreadDumpMonitorContention.java	Wed Jul 05 20:35:10 2017 +0200
@@ -43,7 +43,7 @@
 import java.util.regex.Matcher;
 import java.util.regex.Pattern;
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class TestThreadDumpMonitorContention {
     // jstack tends to be closely bound to the VM that we are running
--- a/hotspot/test/runtime/Thread/ThreadPriorities.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Thread/ThreadPriorities.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,8 +38,8 @@
 import java.util.regex.Matcher;
 import java.util.regex.Pattern;
 
-import com.oracle.java.testlibrary.*;
-import static com.oracle.java.testlibrary.Asserts.*;
+import jdk.test.lib.*;
+import static jdk.test.lib.Asserts.*;
 
 public class ThreadPriorities {
 
--- a/hotspot/test/runtime/Unsafe/AllocateInstance.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/AllocateInstance.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,9 +30,9 @@
  * @run main AllocateInstance
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class AllocateInstance {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/Unsafe/AllocateMemory.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/AllocateMemory.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,9 +30,9 @@
  * @run main/othervm -XX:+UnlockDiagnosticVMOptions -XX:MallocMaxTestWords=100m AllocateMemory
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class AllocateMemory {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/Unsafe/CopyMemory.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/CopyMemory.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,9 +30,9 @@
  * @run main CopyMemory
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class CopyMemory {
     final static int LENGTH = 8;
--- a/hotspot/test/runtime/Unsafe/DefineClass.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/DefineClass.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,9 +33,9 @@
 
 import java.security.ProtectionDomain;
 import java.io.InputStream;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class DefineClass {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/Unsafe/FieldOffset.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/FieldOffset.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,10 +31,10 @@
  */
 
 import java.lang.reflect.Field;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
 import java.lang.reflect.*;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class FieldOffset {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/Unsafe/GetField.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/GetField.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,10 +30,10 @@
  * @run main GetField
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
 import java.lang.reflect.*;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class GetField {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/Unsafe/GetKlassPointerGetJavaMirror.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/GetKlassPointerGetJavaMirror.java	Wed Jul 05 20:35:10 2017 +0200
@@ -25,12 +25,13 @@
  * @bug 8022853
  * @library /testlibrary
  * @modules java.base/sun.misc
+ * @build jdk.test.lib.*
  * @run main GetKlassPointerGetJavaMirror
  */
 
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
 
 public class GetKlassPointerGetJavaMirror {
--- a/hotspot/test/runtime/Unsafe/GetPutAddress.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/GetPutAddress.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,9 +30,9 @@
  * @run main GetPutAddress
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class GetPutAddress {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/Unsafe/GetPutBoolean.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/GetPutBoolean.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,9 +31,9 @@
  */
 
 import java.lang.reflect.Field;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class GetPutBoolean {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/Unsafe/GetPutByte.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/GetPutByte.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,9 +31,9 @@
  */
 
 import java.lang.reflect.Field;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class GetPutByte {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/Unsafe/GetPutChar.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/GetPutChar.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,9 +31,9 @@
  */
 
 import java.lang.reflect.Field;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class GetPutChar {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/Unsafe/GetPutDouble.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/GetPutDouble.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,9 +31,9 @@
  */
 
 import java.lang.reflect.Field;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class GetPutDouble {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/Unsafe/GetPutFloat.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/GetPutFloat.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,9 +31,9 @@
  */
 
 import java.lang.reflect.Field;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class GetPutFloat {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/Unsafe/GetPutInt.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/GetPutInt.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,9 +30,9 @@
  */
 
 import java.lang.reflect.Field;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class GetPutInt {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/Unsafe/GetPutLong.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/GetPutLong.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,9 +31,9 @@
  */
 
 import java.lang.reflect.Field;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class GetPutLong {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/Unsafe/GetPutObject.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/GetPutObject.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,9 +31,9 @@
  */
 
 import java.lang.reflect.Field;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class GetPutObject {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/Unsafe/GetPutShort.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/GetPutShort.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,9 +31,9 @@
  */
 
 import java.lang.reflect.Field;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class GetPutShort {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/Unsafe/GetUncompressedObject.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/GetUncompressedObject.java	Wed Jul 05 20:35:10 2017 +0200
@@ -25,12 +25,13 @@
  * @bug 8022853
  * @library /testlibrary
  * @modules java.base/sun.misc
+ * @build jdk.test.lib.*
  * @run main GetUncompressedObject
  */
 
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
 
 public class GetUncompressedObject {
--- a/hotspot/test/runtime/Unsafe/GetUnsafe.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/GetUnsafe.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  */
 
 import sun.misc.Unsafe;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class GetUnsafe {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/Unsafe/PageSize.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/PageSize.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,9 +31,9 @@
  */
 
 import java.lang.reflect.Field;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class PageSize {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/Unsafe/RangeCheck.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/RangeCheck.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
 
 public class RangeCheck {
--- a/hotspot/test/runtime/Unsafe/Reallocate.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/Reallocate.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,9 +30,9 @@
  * @run main/othervm -XX:+UnlockDiagnosticVMOptions -XX:MallocMaxTestWords=100m Reallocate
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class Reallocate {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/Unsafe/SetMemory.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/SetMemory.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,9 +30,9 @@
  * @run main SetMemory
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class SetMemory {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/Unsafe/ThrowException.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/Unsafe/ThrowException.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,9 +30,9 @@
  * @run main ThrowException
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.misc.Unsafe;
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 public class ThrowException {
     public static void main(String args[]) throws Exception {
--- a/hotspot/test/runtime/XCheckJniJsig/XCheckJSig.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/XCheckJniJsig/XCheckJSig.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
 
 import java.io.File;
 import java.util.Map;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class XCheckJSig {
     public static void main(String args[]) throws Throwable {
--- a/hotspot/test/runtime/classFileParserBug/ClassFileParserBug.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/classFileParserBug/ClassFileParserBug.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  */
 
 import java.io.File;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class ClassFileParserBug {
     public static void main(String args[]) throws Throwable {
--- a/hotspot/test/runtime/classFileParserBug/TestEmptyBootstrapMethodsAttr.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/classFileParserBug/TestEmptyBootstrapMethodsAttr.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
  */
 
 import java.io.File;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class TestEmptyBootstrapMethodsAttr {
 
--- a/hotspot/test/runtime/contended/Options.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/contended/Options.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 /*
  * @test
--- a/hotspot/test/runtime/duplAttributes/DuplAttributesTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/duplAttributes/DuplAttributesTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  */
 
 import java.io.File;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 public class DuplAttributesTest {
 
--- a/hotspot/test/runtime/memory/LargePages/TestLargePageSizeInBytes.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/memory/LargePages/TestLargePageSizeInBytes.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,9 +30,9 @@
  * @run driver TestLargePageSizeInBytes
  */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.Platform;
+import jdk.test.lib.ProcessTools;
 
 public class TestLargePageSizeInBytes {
     private static long M = 1024L * 1024L;
--- a/hotspot/test/runtime/memory/LargePages/TestLargePagesFlags.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/memory/LargePages/TestLargePagesFlags.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,9 +29,9 @@
  * @run main TestLargePagesFlags
  */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.Platform;
+import jdk.test.lib.ProcessTools;
 import java.util.ArrayList;
 
 public class TestLargePagesFlags {
--- a/hotspot/test/runtime/memory/ReadFromNoaccessArea.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/memory/ReadFromNoaccessArea.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
  * @run main ReadFromNoaccessArea
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.hotspot.WhiteBox;
 
 public class ReadFromNoaccessArea {
--- a/hotspot/test/runtime/memory/ReadVMPageSize.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/memory/ReadVMPageSize.java	Wed Jul 05 20:35:10 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
@@ -30,7 +30,7 @@
  * @run main/othervm  -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI  ReadVMPageSize
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.hotspot.WhiteBox;
 
 public class ReadVMPageSize {
--- a/hotspot/test/runtime/memory/ReserveMemory.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/memory/ReserveMemory.java	Wed Jul 05 20:35:10 2017 +0200
@@ -35,7 +35,7 @@
  * @run main ReserveMemory
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 import sun.hotspot.WhiteBox;
 
--- a/hotspot/test/runtime/memory/RunUnitTestsConcurrently.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/memory/RunUnitTestsConcurrently.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
  * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI RunUnitTestsConcurrently 30 15000
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.hotspot.WhiteBox;
 
 public class RunUnitTestsConcurrently {
--- a/hotspot/test/runtime/verifier/OverriderMsg.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/verifier/OverriderMsg.java	Wed Jul 05 20:35:10 2017 +0200
@@ -26,7 +26,7 @@
 import jdk.internal.org.objectweb.asm.ClassWriter;
 import jdk.internal.org.objectweb.asm.MethodVisitor;
 import static jdk.internal.org.objectweb.asm.Opcodes.*;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 /*
  * @test OverriderMsg
--- a/hotspot/test/runtime/verifier/TestANewArray.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/verifier/TestANewArray.java	Wed Jul 05 20:35:10 2017 +0200
@@ -28,7 +28,7 @@
 import jdk.internal.org.objectweb.asm.MethodVisitor;
 import static jdk.internal.org.objectweb.asm.Opcodes.*;
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 /*
  * @test
--- a/hotspot/test/runtime/verifier/TestMultiANewArray.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/runtime/verifier/TestMultiANewArray.java	Wed Jul 05 20:35:10 2017 +0200
@@ -26,7 +26,7 @@
 import jdk.internal.org.objectweb.asm.ClassWriter;
 import jdk.internal.org.objectweb.asm.MethodVisitor;
 import static jdk.internal.org.objectweb.asm.Opcodes.*;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 /*
  * @test TestMultiANewArray
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/runtime/verifier/TraceClassRes.java	Wed Jul 05 20:35:10 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.
+ *
+ * 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 8076318
+ * @summary split verifier needs to add TraceClassResolution
+ * @library /testlibrary
+ */
+
+import jdk.test.lib.*;
+
+// Test that the verifier outputs the classes it loads if -XX:+TraceClassResolution is specified"
+public class TraceClassRes {
+  public static void main(String[] args) throws Exception {
+
+    ProcessBuilder pb = ProcessTools.createJavaProcessBuilder(
+        "-XX:+TraceClassResolution", "-verify", "-Xshare:off", "-version");
+
+    OutputAnalyzer output = new OutputAnalyzer(pb.start());
+    output.shouldContain("RESOLVE java.lang.ClassLoader java.lang.Throwable ClassLoader.java (verification)");
+    output.shouldHaveExitValue(0);
+  }
+}
--- a/hotspot/test/serviceability/attach/AttachSetGetFlag.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/attach/AttachSetGetFlag.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,7 +31,7 @@
  *          java.management
  *          jdk.attach/sun.tools.attach
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.* AttachSetGetFlag
+ * @build jdk.test.lib.* AttachSetGetFlag
  * @run driver AttachSetGetFlag
  */
 
@@ -45,9 +45,9 @@
 
 import sun.tools.attach.HotSpotVirtualMachine;
 
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.Platform;
+import jdk.test.lib.ProcessTools;
 import com.sun.tools.attach.VirtualMachine;
 
 public class AttachSetGetFlag {
--- a/hotspot/test/serviceability/attach/AttachWithStalePidFile.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/attach/AttachWithStalePidFile.java	Wed Jul 05 20:35:10 2017 +0200
@@ -27,11 +27,11 @@
  * @key regression
  * @summary Regression test for attach issue where stale pid files in /tmp lead to connection issues
  * @library /testlibrary
- * @build com.oracle.java.testlibrary.* AttachWithStalePidFileTarget
+ * @build jdk.test.lib.* AttachWithStalePidFileTarget
  * @run main AttachWithStalePidFile
  */
 
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import com.sun.tools.attach.VirtualMachine;
 import sun.tools.attach.HotSpotVirtualMachine;
 import java.lang.reflect.Field;
--- a/hotspot/test/serviceability/dcmd/compiler/CodeCacheTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/compiler/CodeCacheTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,8 +29,8 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
  * @run testng/othervm -XX:+SegmentedCodeCache CodeCacheTest
  * @run testng/othervm -XX:-SegmentedCodeCache CodeCacheTest
  * @run testng/othervm -Xint -XX:+SegmentedCodeCache CodeCacheTest
@@ -40,9 +40,9 @@
 import org.testng.annotations.Test;
 import org.testng.Assert;
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.dcmd.CommandExecutor;
-import com.oracle.java.testlibrary.dcmd.JMXExecutor;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.dcmd.CommandExecutor;
+import jdk.test.lib.dcmd.JMXExecutor;
 
 import java.util.Iterator;
 import java.util.regex.Matcher;
--- a/hotspot/test/serviceability/dcmd/compiler/CodelistTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/compiler/CodelistTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,8 +29,8 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
  * @build MethodIdentifierParser
  * @run testng CodelistTest
  * @summary Test of diagnostic command Compiler.codelist
@@ -39,9 +39,9 @@
 import org.testng.annotations.Test;
 import org.testng.Assert;
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.dcmd.CommandExecutor;
-import com.oracle.java.testlibrary.dcmd.JMXExecutor;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.dcmd.CommandExecutor;
+import jdk.test.lib.dcmd.JMXExecutor;
 
 import java.lang.reflect.Method;
 
--- a/hotspot/test/serviceability/dcmd/compiler/CompilerQueueTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/compiler/CompilerQueueTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,17 +30,17 @@
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
  * @ignore 8069160
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
  * @run testng CompilerQueueTest
  * @run testng/othervm -XX:-TieredCompilation CompilerQueueTest
  * @run testng/othervm -Xint CompilerQueueTest
  * @summary Test of diagnostic command Compiler.queue
  */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.dcmd.CommandExecutor;
-import com.oracle.java.testlibrary.dcmd.JMXExecutor;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.dcmd.CommandExecutor;
+import jdk.test.lib.dcmd.JMXExecutor;
 import org.testng.annotations.Test;
 
 import java.util.Iterator;
--- a/hotspot/test/serviceability/dcmd/framework/HelpTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/framework/HelpTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,12 +21,12 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.dcmd.CommandExecutor;
-import com.oracle.java.testlibrary.dcmd.PidJcmdExecutor;
-import com.oracle.java.testlibrary.dcmd.MainClassJcmdExecutor;
-import com.oracle.java.testlibrary.dcmd.FileJcmdExecutor;
-import com.oracle.java.testlibrary.dcmd.JMXExecutor;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.dcmd.CommandExecutor;
+import jdk.test.lib.dcmd.PidJcmdExecutor;
+import jdk.test.lib.dcmd.MainClassJcmdExecutor;
+import jdk.test.lib.dcmd.FileJcmdExecutor;
+import jdk.test.lib.dcmd.JMXExecutor;
 import org.testng.annotations.Test;
 
 /*
@@ -38,8 +38,8 @@
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
  * @ignore 8072440
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
  * @run testng/othervm -XX:+UsePerfData HelpTest
  */
 public class HelpTest {
--- a/hotspot/test/serviceability/dcmd/framework/InvalidCommandTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/framework/InvalidCommandTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,12 +21,12 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.dcmd.CommandExecutor;
-import com.oracle.java.testlibrary.dcmd.PidJcmdExecutor;
-import com.oracle.java.testlibrary.dcmd.MainClassJcmdExecutor;
-import com.oracle.java.testlibrary.dcmd.FileJcmdExecutor;
-import com.oracle.java.testlibrary.dcmd.JMXExecutor;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.dcmd.CommandExecutor;
+import jdk.test.lib.dcmd.PidJcmdExecutor;
+import jdk.test.lib.dcmd.MainClassJcmdExecutor;
+import jdk.test.lib.dcmd.FileJcmdExecutor;
+import jdk.test.lib.dcmd.JMXExecutor;
 import org.testng.annotations.Test;
 
 /*
@@ -38,8 +38,8 @@
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
  * @ignore 8072440
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
  * @run testng/othervm -XX:+UsePerfData InvalidCommandTest
  */
 public class InvalidCommandTest {
--- a/hotspot/test/serviceability/dcmd/framework/VMVersionTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/framework/VMVersionTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,12 +21,12 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.dcmd.CommandExecutor;
-import com.oracle.java.testlibrary.dcmd.PidJcmdExecutor;
-import com.oracle.java.testlibrary.dcmd.MainClassJcmdExecutor;
-import com.oracle.java.testlibrary.dcmd.FileJcmdExecutor;
-import com.oracle.java.testlibrary.dcmd.JMXExecutor;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.dcmd.CommandExecutor;
+import jdk.test.lib.dcmd.PidJcmdExecutor;
+import jdk.test.lib.dcmd.MainClassJcmdExecutor;
+import jdk.test.lib.dcmd.FileJcmdExecutor;
+import jdk.test.lib.dcmd.JMXExecutor;
 
 import org.testng.annotations.Test;
 
@@ -39,8 +39,8 @@
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
  * @ignore 8072440
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
  * @run testng/othervm -XX:+UsePerfData VMVersionTest
  */
 public class VMVersionTest {
--- a/hotspot/test/serviceability/dcmd/gc/ClassHistogramAllTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/gc/ClassHistogramAllTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,8 +29,8 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
  * @build ClassHistogramTest
  * @run testng ClassHistogramAllTest
  */
--- a/hotspot/test/serviceability/dcmd/gc/ClassHistogramTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/gc/ClassHistogramTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -25,9 +25,9 @@
 
 import java.util.regex.Pattern;
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.dcmd.CommandExecutor;
-import com.oracle.java.testlibrary.dcmd.JMXExecutor;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.dcmd.CommandExecutor;
+import jdk.test.lib.dcmd.JMXExecutor;
 
 /*
  * @test
@@ -37,8 +37,8 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
  * @run testng ClassHistogramTest
  */
 public class ClassHistogramTest {
--- a/hotspot/test/serviceability/dcmd/gc/HeapDumpAllTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/gc/HeapDumpAllTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -25,12 +25,17 @@
  * @test
  * @summary Test of diagnostic command GC.heap_dump -all=true
  * @library /testlibrary
+ * @library /../../test/lib/share/classes
  * @modules java.base/sun.misc
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
+ * @build jdk.test.lib.hprof.*
+ * @build jdk.test.lib.hprof.module.*
+ * @build jdk.test.lib.hprof.parser.*
+ * @build jdk.test.lib.hprof.utils.*
  * @build HeapDumpTest
  * @run testng HeapDumpAllTest
  */
--- a/hotspot/test/serviceability/dcmd/gc/HeapDumpTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/gc/HeapDumpTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -24,70 +24,73 @@
 import org.testng.annotations.Test;
 import org.testng.Assert;
 
+import java.io.File;
+import java.nio.file.Files;
 import java.io.IOException;
+import java.util.List;
 
-import com.oracle.java.testlibrary.JDKToolFinder;
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.dcmd.CommandExecutor;
-import com.oracle.java.testlibrary.dcmd.PidJcmdExecutor;
+import jdk.test.lib.hprof.HprofParser;
+import jdk.test.lib.hprof.model.Snapshot;
+
+import jdk.test.lib.JDKToolFinder;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.dcmd.CommandExecutor;
+import jdk.test.lib.dcmd.PidJcmdExecutor;
 
 /*
  * @test
  * @summary Test of diagnostic command GC.heap_dump
  * @library /testlibrary
+ * @library /../../test/lib/share/classes
  * @modules java.base/sun.misc
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
+ * @build jdk.test.lib.hprof.*
+ * @build jdk.test.lib.hprof.module.*
+ * @build jdk.test.lib.hprof.parser.*
+ * @build jdk.test.lib.hprof.utils.*
  * @run testng HeapDumpTest
  */
 public class HeapDumpTest {
     protected String heapDumpArgs = "";
 
-    public void run(CommandExecutor executor) {
-        String fileName = "jcmd.gc.heap_dump." + System.currentTimeMillis() + ".hprof";
-        String cmd = "GC.heap_dump " + heapDumpArgs + " " + fileName;
+    public void run(CommandExecutor executor) throws IOException {
+        File dump = new File("jcmd.gc.heap_dump." + System.currentTimeMillis() + ".hprof");
+        if (dump.exists()) {
+            dump.delete();
+        }
+
+        String cmd = "GC.heap_dump " + heapDumpArgs + " " + dump.getAbsolutePath();
         executor.execute(cmd);
 
-        verifyHeapDump(fileName);
+        dump.delete();
     }
 
-    private void verifyHeapDump(String fileName) {
-        String jhat = JDKToolFinder.getJDKTool("jhat");
-        String[] cmd = { jhat, "-parseonly", "true", fileName };
-
-        ProcessBuilder pb = new ProcessBuilder(cmd);
-        pb.redirectErrorStream(true);
-        Process p = null;
-        OutputAnalyzer output = null;
-
+    private void verifyHeapDump(File dump) {
+        Assert.assertTrue(dump.exists() && dump.isFile(), "Could not create dump file " + dump.getAbsolutePath());
         try {
-            p = pb.start();
-            output = new OutputAnalyzer(p);
+            File out = HprofParser.parse(dump);
 
-            /*
-             * Some hprof dumps of all objects contain constantPoolOop references that cannot be resolved, so we ignore
-             * failures about resolving constantPoolOop fields using a negative lookahead
-             */
-            output.shouldNotMatch(".*WARNING(?!.*Failed to resolve object.*constantPoolOop.*).*");
-        } catch (IOException e) {
-            Assert.fail("Test error: Caught exception while reading stdout/err of jhat", e);
-        } finally {
-            if (p != null) {
-                p.destroy();
+            Assert.assertTrue(out != null && out.exists() && out.isFile(), "Could not find hprof parser output file");
+            List<String> lines = Files.readAllLines(out.toPath());
+            Assert.assertTrue(lines.size() > 0, "hprof parser output file is empty");
+            for (String line : lines) {
+                Assert.assertFalse(line.matches(".*WARNING(?!.*Failed to resolve object.*constantPoolOop.*).*"));
             }
-        }
 
-        if (output.getExitValue() != 0) {
-            Assert.fail("Test error: jhat exit code was nonzero");
+            out.delete();
+        } catch (Exception e) {
+            e.printStackTrace();
+            Assert.fail("Could not parse dump file " + dump.getAbsolutePath());
         }
     }
 
     /* GC.heap_dump is not available over JMX, running jcmd pid executor instead */
     @Test
-    public void pid() {
+    public void pid() throws IOException {
         run(new PidJcmdExecutor());
     }
 }
--- a/hotspot/test/serviceability/dcmd/gc/RunFinalizationTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/gc/RunFinalizationTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -28,8 +28,8 @@
 import java.util.concurrent.locks.Condition;
 import java.util.concurrent.locks.ReentrantLock;
 
-import com.oracle.java.testlibrary.dcmd.CommandExecutor;
-import com.oracle.java.testlibrary.dcmd.JMXExecutor;
+import jdk.test.lib.dcmd.CommandExecutor;
+import jdk.test.lib.dcmd.JMXExecutor;
 
 /*
  * @test
@@ -39,8 +39,8 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
  * @run testng RunFinalizationTest
  */
 public class RunFinalizationTest {
--- a/hotspot/test/serviceability/dcmd/gc/RunGCTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/gc/RunGCTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,9 +29,9 @@
 import java.nio.file.Path;
 import java.nio.file.Paths;
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.dcmd.CommandExecutor;
-import com.oracle.java.testlibrary.dcmd.JMXExecutor;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.dcmd.CommandExecutor;
+import jdk.test.lib.dcmd.JMXExecutor;
 
 /*
  * @test
@@ -41,8 +41,8 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
  * @run testng/othervm -XX:+PrintGCDetails -Xloggc:RunGC.gclog -XX:-ExplicitGCInvokesConcurrent RunGCTest
  */
 public class RunGCTest {
--- a/hotspot/test/serviceability/dcmd/jvmti/DataDumpDcmdTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/jvmti/DataDumpDcmdTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,10 +21,10 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.dcmd.CommandExecutor;
-import com.oracle.java.testlibrary.dcmd.JMXExecutor;
-import com.oracle.java.testlibrary.dcmd.PidJcmdExecutor;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.dcmd.CommandExecutor;
+import jdk.test.lib.dcmd.JMXExecutor;
+import jdk.test.lib.dcmd.PidJcmdExecutor;
 import org.testng.annotations.Test;
 
 /*
@@ -32,7 +32,7 @@
  * @bug 8054890
  * @summary Test of JVMTI.data_dump diagnostic command
  * @library /testlibrary
- * @build com.oracle.java.testlibrary.*
+ * @build jdk.test.lib.*
  * @run testng DataDumpDcmdTest
  */
 
@@ -57,4 +57,4 @@
     public void cli() throws Throwable {
         run(new PidJcmdExecutor());
     }
-}
\ No newline at end of file
+}
--- a/hotspot/test/serviceability/dcmd/thread/PrintConcurrentLocksTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/thread/PrintConcurrentLocksTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,8 +29,8 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
  * @build PrintTest
  * @run testng PrintConcurrentLocksTest
  */
--- a/hotspot/test/serviceability/dcmd/thread/PrintTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/thread/PrintTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -24,10 +24,10 @@
 import org.testng.annotations.Test;
 import org.testng.Assert;
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
+import jdk.test.lib.OutputAnalyzer;
 
-import com.oracle.java.testlibrary.dcmd.CommandExecutor;
-import com.oracle.java.testlibrary.dcmd.JMXExecutor;
+import jdk.test.lib.dcmd.CommandExecutor;
+import jdk.test.lib.dcmd.JMXExecutor;
 
 import java.util.concurrent.BrokenBarrierException;
 import java.util.concurrent.CyclicBarrier;
@@ -42,8 +42,8 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
  * @run testng PrintTest
  */
 public class PrintTest {
@@ -149,8 +149,8 @@
          *       at java.lang.Object.wait(Object.java:502)
          *        at java.lang.UNIXProcess.waitFor(UNIXProcess.java:397)
          *        - locked <0x000000071a70ad98> (a java.lang.UNIXProcess)
-         *        at com.oracle.java.testlibrary.dcmd.JcmdExecutor.executeImpl(JcmdExecutor.java:32)
-         *       at com.oracle.java.testlibrary.dcmd.CommandExecutor.execute(CommandExecutor.java:24)
+         *        at jdk.test.lib.dcmd.JcmdExecutor.executeImpl(JcmdExecutor.java:32)
+         *       at jdk.test.lib.dcmd.CommandExecutor.execute(CommandExecutor.java:24)
          * -->   at Print.run(Print.java:74)
          *       at Print.file(Print.java:112)
          *     ...
--- a/hotspot/test/serviceability/dcmd/vm/ClassHierarchyTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/vm/ClassHierarchyTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,17 +29,17 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
  * @run testng ClassHierarchyTest
  */
 
 import org.testng.annotations.Test;
 import org.testng.Assert;
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.dcmd.CommandExecutor;
-import com.oracle.java.testlibrary.dcmd.JMXExecutor;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.dcmd.CommandExecutor;
+import jdk.test.lib.dcmd.JMXExecutor;
 
 import java.io.File;
 import java.io.FileInputStream;
--- a/hotspot/test/serviceability/dcmd/vm/ClassLoaderStatsTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/vm/ClassLoaderStatsTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,17 +29,17 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
  * @run testng ClassLoaderStatsTest
  */
 
 import org.testng.annotations.Test;
 import org.testng.Assert;
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.dcmd.CommandExecutor;
-import com.oracle.java.testlibrary.dcmd.JMXExecutor;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.dcmd.CommandExecutor;
+import jdk.test.lib.dcmd.JMXExecutor;
 
 import java.io.File;
 import java.io.FileInputStream;
--- a/hotspot/test/serviceability/dcmd/vm/CommandLineTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/vm/CommandLineTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,11 +21,11 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
+import jdk.test.lib.OutputAnalyzer;
 import org.testng.annotations.Test;
 
-import com.oracle.java.testlibrary.dcmd.CommandExecutor;
-import com.oracle.java.testlibrary.dcmd.JMXExecutor;
+import jdk.test.lib.dcmd.CommandExecutor;
+import jdk.test.lib.dcmd.JMXExecutor;
 
 /*
  * @test
@@ -35,8 +35,8 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
  * @run testng/othervm -XX:+IgnoreUnrecognizedVMOptions -XX:+ThereShouldNotBeAnyVMOptionNamedLikeThis CommandLineTest
  */
 public class CommandLineTest {
--- a/hotspot/test/serviceability/dcmd/vm/DynLibsTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/vm/DynLibsTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,10 +1,10 @@
 import org.testng.annotations.Test;
 import org.testng.Assert;
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.dcmd.CommandExecutor;
-import com.oracle.java.testlibrary.dcmd.JMXExecutor;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.Platform;
+import jdk.test.lib.dcmd.CommandExecutor;
+import jdk.test.lib.dcmd.JMXExecutor;
 
 /*
  * Copyright (c) 2013, 2015, Oracle and/or its affiliates. All rights reserved.
@@ -37,8 +37,8 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
  * @run testng DynLibsTest
  */
 
--- a/hotspot/test/serviceability/dcmd/vm/FlagsTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/vm/FlagsTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,9 +21,9 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.dcmd.CommandExecutor;
-import com.oracle.java.testlibrary.dcmd.JMXExecutor;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.dcmd.CommandExecutor;
+import jdk.test.lib.dcmd.JMXExecutor;
 import org.testng.annotations.Test;
 
 /*
@@ -34,8 +34,8 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
  * @run testng/othervm -Xmx129m -XX:+PrintGC -XX:+UnlockDiagnosticVMOptions -XX:+IgnoreUnrecognizedVMOptions -XX:+ThereShouldNotBeAnyVMOptionNamedLikeThis_Right -XX:-TieredCompilation FlagsTest
  */
 public class FlagsTest {
--- a/hotspot/test/serviceability/dcmd/vm/SetVMFlagTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/vm/SetVMFlagTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,9 +21,9 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.dcmd.CommandExecutor;
-import com.oracle.java.testlibrary.dcmd.JMXExecutor;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.dcmd.CommandExecutor;
+import jdk.test.lib.dcmd.JMXExecutor;
 import org.testng.annotations.Test;
 import static org.testng.Assert.*;
 
@@ -32,8 +32,8 @@
  * @bug 8054890
  * @summary Test of VM.set_flag diagnostic command
  * @library /testlibrary
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
  * @run testng SetVMFlagTest
  */
 
@@ -139,4 +139,4 @@
     private OutputAnalyzer getAllFlags(CommandExecutor executor) {
         return executor.execute("VM.flags -all", true);
     }
-}
\ No newline at end of file
+}
--- a/hotspot/test/serviceability/dcmd/vm/SystemPropertiesTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/vm/SystemPropertiesTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -23,9 +23,9 @@
 
 import org.testng.annotations.Test;
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.dcmd.CommandExecutor;
-import com.oracle.java.testlibrary.dcmd.JMXExecutor;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.dcmd.CommandExecutor;
+import jdk.test.lib.dcmd.JMXExecutor;
 
 /*
  * @test
@@ -35,8 +35,8 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
  * @run testng SystemPropertiesTest
  */
 public class SystemPropertiesTest {
--- a/hotspot/test/serviceability/dcmd/vm/UptimeTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/dcmd/vm/UptimeTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -24,9 +24,9 @@
 import org.testng.annotations.Test;
 import org.testng.Assert;
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.dcmd.CommandExecutor;
-import com.oracle.java.testlibrary.dcmd.JMXExecutor;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.dcmd.CommandExecutor;
+import jdk.test.lib.dcmd.JMXExecutor;
 
 import java.text.NumberFormat;
 import java.text.ParseException;
@@ -39,8 +39,8 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.*
- * @build com.oracle.java.testlibrary.dcmd.*
+ * @build jdk.test.lib.*
+ * @build jdk.test.lib.dcmd.*
  * @run testng UptimeTest
  */
 public class UptimeTest {
--- a/hotspot/test/serviceability/jvmti/GetObjectSizeOverflow.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/jvmti/GetObjectSizeOverflow.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,7 +21,7 @@
  * questions.
  */
 import java.io.PrintWriter;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 /*
  * Test to verify GetObjectSize does not overflow on a 600M element int[]
@@ -34,7 +34,7 @@
  *          java.instrument
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build ClassFileInstaller com.oracle.java.testlibrary.* GetObjectSizeOverflowAgent
+ * @build ClassFileInstaller jdk.test.lib.* GetObjectSizeOverflowAgent
  * @run main ClassFileInstaller GetObjectSizeOverflowAgent
  * @run main GetObjectSizeOverflow
  */
--- a/hotspot/test/serviceability/jvmti/TestLambdaFormRetransformation.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/jvmti/TestLambdaFormRetransformation.java	Wed Jul 05 20:35:10 2017 +0200
@@ -46,9 +46,9 @@
 import java.security.ProtectionDomain;
 import java.util.Arrays;
 
-import com.oracle.java.testlibrary.ExitCode;
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.ExitCode;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 
 public class TestLambdaFormRetransformation {
     private static String MANIFEST = String.format("Manifest-Version: 1.0\n" +
--- a/hotspot/test/serviceability/jvmti/TestRedefineWithUnresolvedClass.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/jvmti/TestRedefineWithUnresolvedClass.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,15 +32,15 @@
  *          java.management
  *          jdk.jartool/sun.tools.jar
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.* UnresolvedClassAgent
+ * @build jdk.test.lib.* UnresolvedClassAgent
  * @run main TestRedefineWithUnresolvedClass
  */
 
 import java.io.File;
 import java.util.Arrays;
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 
 public class TestRedefineWithUnresolvedClass {
 
--- a/hotspot/test/serviceability/sa/jmap-hashcode/Test8028623.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/sa/jmap-hashcode/Test8028623.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,15 +30,15 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.*
+ * @build jdk.test.lib.*
  * @compile -encoding utf8 Test8028623.java
  * @run main Test8028623
  */
 
-import com.oracle.java.testlibrary.JDKToolLauncher;
-import com.oracle.java.testlibrary.OutputBuffer;
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.JDKToolLauncher;
+import jdk.test.lib.OutputBuffer;
+import jdk.test.lib.Platform;
+import jdk.test.lib.ProcessTools;
 
 import java.io.File;
 
--- a/hotspot/test/serviceability/sa/jmap-hprof/JMapHProfLargeHeapTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/sa/jmap-hprof/JMapHProfLargeHeapTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,12 +31,12 @@
 import java.util.Arrays;
 import java.util.Scanner;
 
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.JDKToolFinder;
-import com.oracle.java.testlibrary.JDKToolLauncher;
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.Platform;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.JDKToolFinder;
+import jdk.test.lib.JDKToolLauncher;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.Platform;
+import jdk.test.lib.ProcessTools;
 
 /*
  * @test
@@ -48,7 +48,7 @@
  *          java.compiler
  *          java.management/sun.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build com.oracle.java.testlibrary.* JMapHProfLargeHeapProc
+ * @build jdk.test.lib.* JMapHProfLargeHeapProc
  * @run main JMapHProfLargeHeapTest
  */
 
--- a/hotspot/test/serviceability/threads/TestFalseDeadLock.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/serviceability/threads/TestFalseDeadLock.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.Utils;
 import java.lang.management.ManagementFactory;
 import java.lang.management.ThreadMXBean;
 import java.util.Random;
--- a/hotspot/test/test_env.sh	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/test_env.sh	Wed Jul 05 20:35:10 2017 +0200
@@ -188,6 +188,10 @@
 if [ $? = 0 ]
 then
   VM_CPU="ppc"
+  if [ $VM_BITS = "64" ]
+  then
+    VM_CPU="ppc64"
+  fi
 fi
 grep "ia64" vm_version.out > ${NULL}
 if [ $? = 0 ]
--- a/hotspot/test/testlibrary/RedefineClassHelper.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/testlibrary/RedefineClassHelper.java	Wed Jul 05 20:35:10 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
@@ -23,7 +23,7 @@
 
 import java.io.PrintWriter;
 import java.lang.instrument.*;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 
 /*
  * Helper class to write tests that redefine classes.
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/Asserts.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,451 +0,0 @@
-/*
- * 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.
- */
-
-package com.oracle.java.testlibrary;
-
-/**
- * Asserts that can be used for verifying assumptions in tests.
- *
- * An assertion will throw a {@link RuntimeException} if the assertion isn't
- * valid.  All the asserts can be imported into a test by using a static
- * import:
- *
- * <pre>
- * {@code
- * import static com.oracle.java.testlibrary.Asserts.*;
- * }
- *
- * Always provide a message describing the assumption if the line number of the
- * failing assertion isn't enough to understand why the assumption failed. For
- * example, if the assertion is in a loop or in a method that is called
- * multiple times, then the line number won't provide enough context to
- * understand the failure.
- * </pre>
- */
-public class Asserts {
-
-    /**
-     * Shorthand for {@link #assertLessThan(T, T)}.
-     *
-     * @see #assertLessThan(T, T)
-     */
-    public static <T extends Comparable<T>> void assertLT(T lhs, T rhs) {
-        assertLessThan(lhs, rhs);
-    }
-
-    /**
-     * Shorthand for {@link #assertLessThan(T, T, String)}.
-     *
-     * @see #assertLessThan(T, T, String)
-     */
-    public static <T extends Comparable<T>> void assertLT(T lhs, T rhs, String msg) {
-        assertLessThan(lhs, rhs, msg);
-    }
-
-    /**
-     * Calls {@link #assertLessThan(T, T, String)} with a default message.
-     *
-     * @see #assertLessThan(T, T, String)
-     */
-    public static <T extends Comparable<T>> void assertLessThan(T lhs, T rhs) {
-        assertLessThan(lhs, rhs, null);
-    }
-
-    /**
-     * Asserts that {@code lhs} is less than {@code rhs}.
-     *
-     * @param lhs The left hand side of the comparison.
-     * @param rhs The right hand side of the comparison.
-     * @param msg A description of the assumption.
-     * @throws RuntimeException if the assertion isn't valid.
-     */
-    public static <T extends Comparable<T>>void assertLessThan(T lhs, T rhs, String msg) {
-        assertTrue(compare(lhs, rhs, msg) < 0, getMessage(lhs, rhs, "<", msg));
-    }
-
-    /**
-     * Shorthand for {@link #assertLessThanOrEqual(T, T)}.
-     *
-     * @see #assertLessThanOrEqual(T, T)
-     */
-    public static <T extends Comparable<T>> void assertLTE(T lhs, T rhs) {
-        assertLessThanOrEqual(lhs, rhs);
-    }
-
-    /**
-     * Shorthand for {@link #assertLessThanOrEqual(T, T, String)}.
-     *
-     * @see #assertLessThanOrEqual(T, T, String)
-     */
-    public static <T extends Comparable<T>> void assertLTE(T lhs, T rhs, String msg) {
-        assertLessThanOrEqual(lhs, rhs, msg);
-    }
-
-    /**
-     * Calls {@link #assertLessThanOrEqual(T, T, String)} with a default message.
-     *
-     * @see #assertLessThanOrEqual(T, T, String)
-     */
-    public static <T extends Comparable<T>> void assertLessThanOrEqual(T lhs, T rhs) {
-        assertLessThanOrEqual(lhs, rhs, null);
-    }
-
-    /**
-     * Asserts that {@code lhs} is less than or equal to {@code rhs}.
-     *
-     * @param lhs The left hand side of the comparison.
-     * @param rhs The right hand side of the comparison.
-     * @param msg A description of the assumption.
-     * @throws RuntimeException if the assertion isn't valid.
-     */
-    public static <T extends Comparable<T>> void assertLessThanOrEqual(T lhs, T rhs, String msg) {
-        assertTrue(compare(lhs, rhs, msg) <= 0, getMessage(lhs, rhs, "<=", msg));
-    }
-
-    /**
-     * Shorthand for {@link #assertEquals(T, T)}.
-     *
-     * @see #assertEquals(T, T)
-     */
-    public static void assertEQ(Object lhs, Object rhs) {
-        assertEquals(lhs, rhs);
-    }
-
-    /**
-     * Shorthand for {@link #assertEquals(T, T, String)}.
-     *
-     * @see #assertEquals(T, T, String)
-     */
-    public static void assertEQ(Object lhs, Object rhs, String msg) {
-        assertEquals(lhs, rhs, msg);
-    }
-
-    /**
-     * Calls {@link #assertEquals(T, T, String)} with a default message.
-     *
-     * @see #assertEquals(T, T, String)
-     */
-    public static void assertEquals(Object lhs, Object rhs) {
-        assertEquals(lhs, rhs, null);
-    }
-
-    /**
-     * Asserts that {@code lhs} is equal to {@code rhs}.
-     *
-     * @param lhs The left hand side of the comparison.
-     * @param rhs The right hand side of the comparison.
-     * @param msg A description of the assumption.
-     * @throws RuntimeException if the assertion isn't valid.
-     */
-    public static void assertEquals(Object lhs, Object rhs, String msg) {
-        if (lhs == null) {
-            if (rhs != null) {
-                error(msg);
-            }
-        } else {
-            assertTrue(lhs.equals(rhs), getMessage(lhs, rhs, "==", msg));
-        }
-    }
-
-    /**
-     * Shorthand for {@link #assertGreaterThanOrEqual(T, T)}.
-     *
-     * @see #assertGreaterThanOrEqual(T, T)
-     */
-    public static <T extends Comparable<T>> void assertGTE(T lhs, T rhs) {
-        assertGreaterThanOrEqual(lhs, rhs);
-    }
-
-    /**
-     * Shorthand for {@link #assertGreaterThanOrEqual(T, T, String)}.
-     *
-     * @see #assertGreaterThanOrEqual(T, T, String)
-     */
-    public static <T extends Comparable<T>> void assertGTE(T lhs, T rhs, String msg) {
-        assertGreaterThanOrEqual(lhs, rhs, msg);
-    }
-
-    /**
-     * Calls {@link #assertGreaterThanOrEqual(T, T, String)} with a default message.
-     *
-     * @see #assertGreaterThanOrEqual(T, T, String)
-     */
-    public static <T extends Comparable<T>> void assertGreaterThanOrEqual(T lhs, T rhs) {
-        assertGreaterThanOrEqual(lhs, rhs, null);
-    }
-
-    /**
-     * Asserts that {@code lhs} is greater than or equal to {@code rhs}.
-     *
-     * @param lhs The left hand side of the comparison.
-     * @param rhs The right hand side of the comparison.
-     * @param msg A description of the assumption.
-     * @throws RuntimeException if the assertion isn't valid.
-     */
-    public static <T extends Comparable<T>> void assertGreaterThanOrEqual(T lhs, T rhs, String msg) {
-        assertTrue(compare(lhs, rhs, msg) >= 0, getMessage(lhs, rhs, ">=", msg));
-    }
-
-    /**
-     * Shorthand for {@link #assertGreaterThan(T, T)}.
-     *
-     * @see #assertGreaterThan(T, T)
-     */
-    public static <T extends Comparable<T>> void assertGT(T lhs, T rhs) {
-        assertGreaterThan(lhs, rhs);
-    }
-
-    /**
-     * Shorthand for {@link #assertGreaterThan(T, T, String)}.
-     *
-     * @see #assertGreaterThan(T, T, String)
-     */
-    public static <T extends Comparable<T>> void assertGT(T lhs, T rhs, String msg) {
-        assertGreaterThan(lhs, rhs, msg);
-    }
-
-    /**
-     * Calls {@link #assertGreaterThan(T, T, String)} with a default message.
-     *
-     * @see #assertGreaterThan(T, T, String)
-     */
-    public static <T extends Comparable<T>> void assertGreaterThan(T lhs, T rhs) {
-        assertGreaterThan(lhs, rhs, null);
-    }
-
-    /**
-     * Asserts that {@code lhs} is greater than {@code rhs}.
-     *
-     * @param lhs The left hand side of the comparison.
-     * @param rhs The right hand side of the comparison.
-     * @param msg A description of the assumption.
-     * @throws RuntimeException if the assertion isn't valid.
-     */
-    public static <T extends Comparable<T>> void assertGreaterThan(T lhs, T rhs, String msg) {
-        assertTrue(compare(lhs, rhs, msg) > 0, getMessage(lhs, rhs, ">", msg));
-    }
-
-    /**
-     * Shorthand for {@link #assertNotEquals(T, T)}.
-     *
-     * @see #assertNotEquals(T, T)
-     */
-    public static void assertNE(Object lhs, Object rhs) {
-        assertNotEquals(lhs, rhs);
-    }
-
-    /**
-     * Shorthand for {@link #assertNotEquals(T, T, String)}.
-     *
-     * @see #assertNotEquals(T, T, String)
-     */
-    public static void assertNE(Object lhs, Object rhs, String msg) {
-        assertNotEquals(lhs, rhs, msg);
-    }
-
-    /**
-     * Calls {@link #assertNotEquals(T, T, String)} with a default message.
-     *
-     * @see #assertNotEquals(T, T, String)
-     */
-    public static void assertNotEquals(Object lhs, Object rhs) {
-        assertNotEquals(lhs, rhs, null);
-    }
-
-    /**
-     * Asserts that {@code lhs} is not equal to {@code rhs}.
-     *
-     * @param lhs The left hand side of the comparison.
-     * @param rhs The right hand side of the comparison.
-     * @param msg A description of the assumption.
-     * @throws RuntimeException if the assertion isn't valid.
-     */
-    public static void assertNotEquals(Object lhs, Object rhs, String msg) {
-        if (lhs == null) {
-            if (rhs == null) {
-                error(msg);
-            }
-        } else {
-            assertFalse(lhs.equals(rhs), getMessage(lhs, rhs,"!=", msg));
-        }
-    }
-
-    /**
-     * Calls {@link #assertNull(Object, String)} with a default message.
-     *
-     * @see #assertNull(Object, String)
-     */
-    public static void assertNull(Object o) {
-        assertNull(o, "Expected " + format(o) + " to be null");
-    }
-
-    /**
-     * Asserts that {@code o} is null.
-     *
-     * @param o The reference assumed to be null.
-     * @param msg A description of the assumption.
-     * @throws RuntimeException if the assertion isn't valid.
-     */
-    public static void assertNull(Object o, String msg) {
-        assertEquals(o, null, msg);
-    }
-
-    /**
-     * Calls {@link #assertNotNull(Object, String)} with a default message.
-     *
-     * @see #assertNotNull(Object, String)
-     */
-    public static void assertNotNull(Object o) {
-        assertNotNull(o, "Expected non null reference");
-    }
-
-    /**
-     * Asserts that {@code o} is <i>not</i> null.
-     *
-     * @param o The reference assumed <i>not</i> to be null,
-     * @param msg A description of the assumption.
-     * @throws RuntimeException if the assertion isn't valid.
-     */
-    public static void assertNotNull(Object o, String msg) {
-        assertNotEquals(o, null, msg);
-    }
-
-    /**
-     * Calls {@link #assertFalse(boolean, String)} with a default message.
-     *
-     * @see #assertFalse(boolean, String)
-     */
-    public static void assertFalse(boolean value) {
-        assertFalse(value, "Expected value to be false");
-    }
-
-    /**
-     * Asserts that {@code value} is {@code false}.
-     *
-     * @param value The value assumed to be false.
-     * @param msg A description of the assumption.
-     * @throws RuntimeException if the assertion isn't valid.
-     */
-    public static void assertFalse(boolean value, String msg) {
-        assertTrue(!value, msg);
-    }
-
-    /**
-     * Calls {@link #assertTrue(boolean, String)} with a default message.
-     *
-     * @see #assertTrue(boolean, String)
-     */
-    public static void assertTrue(boolean value) {
-        assertTrue(value, "Expected value to be true");
-    }
-
-    /**
-     * Asserts that {@code value} is {@code true}.
-     *
-     * @param value The value assumed to be true.
-     * @param msg A description of the assumption.
-     * @throws RuntimeException if the assertion isn't valid.
-     */
-    public static void assertTrue(boolean value, String msg) {
-        if (!value) {
-            error(msg);
-        }
-    }
-
-    /**
-     * Asserts that two strings are equal.
-     *
-     * If strings are not equals, then exception message
-     * will contain {@code msg} followed by list of mismatched lines.
-     *
-     * @param str1 First string to compare.
-     * @param str2 Second string to compare.
-     * @param msg A description of the assumption.
-     * @throws RuntimeException if strings are not equal.
-     */
-    public static void assertStringsEqual(String str1, String str2,
-                                          String msg) {
-        String lineSeparator = System.getProperty("line.separator");
-        String str1Lines[] = str1.split(lineSeparator);
-        String str2Lines[] = str2.split(lineSeparator);
-
-        int minLength = Math.min(str1Lines.length, str2Lines.length);
-        String longestStringLines[] = ((str1Lines.length == minLength) ?
-                                       str2Lines : str1Lines);
-
-        boolean stringsAreDifferent = false;
-
-        StringBuilder messageBuilder = new StringBuilder(msg);
-
-        messageBuilder.append("\n");
-
-        for (int line = 0; line < minLength; line++) {
-            if (!str1Lines[line].equals(str2Lines[line])) {
-                messageBuilder.append(String.
-                                      format("[line %d] '%s' differs " +
-                                             "from '%s'\n",
-                                             line,
-                                             str1Lines[line],
-                                             str2Lines[line]));
-                stringsAreDifferent = true;
-            }
-        }
-
-        if (minLength < longestStringLines.length) {
-            String stringName = ((longestStringLines == str1Lines) ?
-                                 "first" : "second");
-            messageBuilder.append(String.format("Only %s string contains " +
-                                                "following lines:\n",
-                                                stringName));
-            stringsAreDifferent = true;
-            for(int line = minLength; line < longestStringLines.length; line++) {
-                messageBuilder.append(String.
-                                      format("[line %d] '%s'", line,
-                                             longestStringLines[line]));
-            }
-        }
-
-        if (stringsAreDifferent) {
-            error(messageBuilder.toString());
-        }
-    }
-
-    private static <T extends Comparable<T>> int compare(T lhs, T rhs, String msg) {
-        assertNotNull(lhs, msg);
-        assertNotNull(rhs, msg);
-        return lhs.compareTo(rhs);
-    }
-
-    private static String format(Object o) {
-        return o == null? "null" : o.toString();
-    }
-
-    private static void error(String msg) {
-        throw new RuntimeException(msg);
-    }
-
-    private static String getMessage(Object lhs, Object rhs, String op, String msg) {
-        return (msg == null ? "" : msg + " ") + "(assert failed: " + format(lhs) + " " + op +  " " + format(rhs) + ")";
-    }
-}
-
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/BuildHelper.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,106 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package com.oracle.java.testlibrary;
-
-import java.io.File;
-import java.io.FileReader;
-import java.util.Properties;
-
-public class BuildHelper {
-
-    /**
-     * Commercial builds should have the BUILD_TYPE set to commercial
-     * within the release file, found at the root of the JDK.
-     */
-    public static boolean isCommercialBuild() throws Exception {
-        String buildType = getReleaseProperty("BUILD_TYPE","notFound");
-        return buildType.equals("commercial");
-    }
-
-
-    /**
-     * Return the value for property key, or defaultValue if no property not found.
-     * If present, double quotes are trimmed.
-     */
-    public static String getReleaseProperty(String key, String defaultValue) throws Exception {
-        Properties properties = getReleaseProperties();
-        String value = properties.getProperty(key, defaultValue);
-        return trimDoubleQuotes(value);
-    }
-
-    /**
-     * Return the value for property key, or null if no property not found.
-     * If present, double quotes are trimmed.
-     */
-    public static String getReleaseProperty(String key) throws Exception {
-        return getReleaseProperty(key, null);
-    }
-
-    /**
-     * Get properties from the release file
-     */
-    public static Properties getReleaseProperties() throws Exception {
-        Properties properties = new Properties();
-        properties.load(new FileReader(getReleaseFile()));
-        return properties;
-    }
-
-    /**
-     * Every JDK has a release file in its root.
-     * @return A handler to the release file.
-     */
-    public static File getReleaseFile() throws Exception {
-        String jdkPath = getJDKRoot();
-        File releaseFile = new File(jdkPath,"release");
-        if ( ! releaseFile.canRead() ) {
-            throw new Exception("Release file is not readable, or it is absent: " +
-                    releaseFile.getCanonicalPath());
-        }
-        return releaseFile;
-    }
-
-    /**
-     * Returns path to the JDK under test.
-     * This path is obtained through the test.jdk property, usually set by JTREG.
-     */
-    public static String getJDKRoot() {
-        String jdkPath = System.getProperty("test.jdk");
-        if (jdkPath == null) {
-            throw new RuntimeException("System property 'test.jdk' not set. This property is normally set by jtreg. "
-                    + "When running test separately, set this property using '-Dtest.jdk=/path/to/jdk'.");
-        }
-        return jdkPath;
-    }
-
-    /**
-     * Trim double quotes from the beginning and the end of the given string.
-     * @param original string to trim.
-     * @return a new trimmed string.
-     */
-    public static String trimDoubleQuotes(String original) {
-        if (original == null) { return null; }
-        String trimmed = original.replaceAll("^\"+|\"+$", "");
-        return trimmed;
-    }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/ByteCodeLoader.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,90 +0,0 @@
-/*
- * 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.
- */
-
-package com.oracle.java.testlibrary;
-
-import java.security.SecureClassLoader;
-
-/**
- * {@code ByteCodeLoader} can be used for easy loading of byte code already
- * present in memory.
- *
- * {@code InMemoryCompiler} can be used for compiling source code in a string
- * into byte code, which then can be loaded with {@code ByteCodeLoader}.
- *
- * @see InMemoryCompiler
- */
-public class ByteCodeLoader extends SecureClassLoader {
-    private final String className;
-    private final byte[] byteCode;
-    private volatile Class<?> holder;
-
-    /**
-     * Creates a new {@code ByteCodeLoader} ready to load a class with the
-     * given name and the given byte code.
-     *
-     * @param className The name of the class
-     * @param byteCode The byte code of the class
-     */
-    public ByteCodeLoader(String className, byte[] byteCode) {
-        this.className = className;
-        this.byteCode = byteCode;
-    }
-
-    @Override
-    public Class<?> loadClass(String name) throws ClassNotFoundException {
-        if (!name.equals(className)) {
-            return super.loadClass(name);
-        }
-        if (holder == null) {
-            synchronized(this) {
-                if (holder == null) {
-                    holder = findClass(name);
-                }
-            }
-        }
-        return holder;
-    }
-
-    @Override
-    protected Class<?> findClass(String name) throws ClassNotFoundException {
-        if (!name.equals(className)) {
-            throw new ClassNotFoundException(name);
-        }
-
-        return defineClass(name, byteCode, 0, byteCode.length);
-    }
-
-    /**
-     * Utility method for creating a new {@code ByteCodeLoader} and then
-     * directly load the given byte code.
-     *
-     * @param className The name of the class
-     * @param byteCode The byte code for the class
-     * @throws ClassNotFoundException if the class can't be loaded
-     * @return A {@see Class} object representing the class
-     */
-    public static Class<?> load(String className, byte[] byteCode) throws ClassNotFoundException {
-        return new ByteCodeLoader(className, byteCode).loadClass(className);
-    }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/DynamicVMOption.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,165 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-package com.oracle.java.testlibrary;
-
-import com.sun.management.HotSpotDiagnosticMXBean;
-import java.lang.management.ManagementFactory;
-
-/**
- * A utility class to work with VM options which could be altered during
- * execution.
- *
- * This class is a wrapper around {@code com.sun.management.VMOption}.
- * It provides more convenient interface to read/write the values.
- *
- */
-public class DynamicVMOption {
-
-    private final HotSpotDiagnosticMXBean mxBean;
-
-    /**
-     * VM option name, like "MinHeapFreeRatio".
-     */
-    public final String name;
-
-    /**
-     * Creates an instance of DynamicVMOption.
-     *
-     * @param name the VM option name
-     */
-    public DynamicVMOption(String name) {
-        this.name = name;
-        mxBean = ManagementFactory.getPlatformMXBean(HotSpotDiagnosticMXBean.class);
-    }
-
-    /**
-     * Sets a new value for the option.
-     * Trying to set not applicable value will cause IllegalArgumentException.
-     * Behavior with null is undefined, most likely NPE will be thrown.
-     *
-     * @param newValue the value to be set
-     * @see #getValue()
-     * @throws IllegalArgumentException if newValue is not applicable to the option
-     */
-    public final void setValue(String newValue) {
-        mxBean.setVMOption(name, newValue);
-    }
-
-    /**
-     * Returns the value of option.
-     *
-     * @return the current option value
-     * @see #setValue(java.lang.String)
-     */
-    public final String getValue() {
-        return mxBean.getVMOption(name).getValue();
-    }
-
-    /**
-     * Returns true, if option is writable, false otherwise.
-     *
-     * @return true, if option is writable, false otherwise
-     */
-    public final boolean isWriteable() {
-        return mxBean.getVMOption(name).isWriteable();
-    }
-
-    /**
-     * Checks if the given value is applicable for the option.
-     *
-     * This method tries to set the option to the new value. If no exception
-     * has been thrown the value is treated as valid.
-     *
-     * Calling this method will not change the option value. After an attempt
-     * to set a new value, the option will be restored to its previous value.
-     *
-     * @param value the value to verify
-     * @return true if option could be set to the given value
-     */
-    public boolean isValidValue(String value) {
-        boolean isValid = true;
-        String oldValue = getValue();
-        try {
-            setValue(value);
-        } catch (NullPointerException e) {
-            if (value == null) {
-                isValid = false;
-            }
-        } catch (IllegalArgumentException e) {
-            isValid = false;
-        } finally {
-            setValue(oldValue);
-        }
-        return isValid;
-    }
-
-    /**
-     * Returns the value of the given VM option as String.
-     *
-     * This is a simple shortcut for {@code new DynamicVMOption(name).getValue()}
-     *
-     * @param name the name of VM option
-     * @return value as a string
-     * @see #getValue()
-     */
-    public static String getString(String name) {
-        return new DynamicVMOption(name).getValue();
-    }
-
-    /**
-     * Returns the value of the given option as int.
-     *
-     * @param name the name of VM option
-     * @return value parsed as integer
-     * @see #getString(java.lang.String)
-     *
-     */
-    public static int getInt(String name) {
-        return Integer.parseInt(getString(name));
-    }
-
-    /**
-     * Sets the VM option to a new value.
-     *
-     * This is a simple shortcut for {@code new DynamicVMOption(name).setValue(value)}
-     *
-     * @param name the name of VM option
-     * @param value the value to be set
-     * @see #setValue(java.lang.String)
-     */
-    public static void setString(String name, String value) {
-        new DynamicVMOption(name).setValue(value);
-    }
-
-    /**
-     * Sets the VM option value to a new integer value.
-     *
-     * @param name the name of VM option
-     * @param value the integer value to be set
-     * @see #setString(java.lang.String, java.lang.String)
-     */
-    public static void setInt(String name, int value) {
-        new DynamicVMOption(name).setValue(Integer.toString(value));
-    }
-
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/ExitCode.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,40 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package com.oracle.java.testlibrary;
-
-/**
- * Exit code values that could be returned by the JVM.
- */
-public enum ExitCode {
-    OK(0),
-    FAIL(1),
-    CRASH(134);
-
-    public final int value;
-
-    ExitCode(int value) {
-        this.value = value;
-    }
-}
-
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/InMemoryJavaCompiler.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,154 +0,0 @@
-/*
- * 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.
- */
-
-package com.oracle.java.testlibrary;
-
-import java.io.ByteArrayOutputStream;
-import java.io.IOException;
-import java.io.OutputStream;
-
-import java.net.URI;
-import java.util.Arrays;
-
-import javax.tools.ForwardingJavaFileManager;
-import javax.tools.ForwardingJavaFileManager;
-import javax.tools.FileObject;
-import javax.tools.JavaCompiler;
-import javax.tools.JavaCompiler.CompilationTask;
-import javax.tools.JavaFileManager;
-import javax.tools.JavaFileObject;
-import javax.tools.JavaFileObject.Kind;
-import javax.tools.SimpleJavaFileObject;
-import javax.tools.ToolProvider;
-
-/**
- * {@code InMemoryJavaCompiler} can be used for compiling a {@link
- * CharSequence} to a {@code byte[]}.
- *
- * The compiler will not use the file system at all, instead using a {@link
- * ByteArrayOutputStream} for storing the byte code. For the source code, any
- * kind of {@link CharSequence} can be used, e.g. {@link String}, {@link
- * StringBuffer} or {@link StringBuilder}.
- *
- * The {@code InMemoryCompiler} can easily be used together with a {@code
- * ByteClassLoader} to easily compile and load source code in a {@link String}:
- *
- * <pre>
- * {@code
- * import com.oracle.java.testlibrary.InMemoryJavaCompiler;
- * import com.oracle.java.testlibrary.ByteClassLoader;
- *
- * class Example {
- *     public static void main(String[] args) {
- *         String className = "Foo";
- *         String sourceCode = "public class " + className + " {" +
- *                             "    public void bar() {" +
- *                             "        System.out.println("Hello from bar!");" +
- *                             "    }" +
- *                             "}";
- *         byte[] byteCode = InMemoryJavaCompiler.compile(className, sourceCode);
- *         Class fooClass = ByteClassLoader.load(className, byteCode);
- *     }
- * }
- * }
- * </pre>
- */
-public class InMemoryJavaCompiler {
-    private static class MemoryJavaFileObject extends SimpleJavaFileObject {
-        private final String className;
-        private final CharSequence sourceCode;
-        private final ByteArrayOutputStream byteCode;
-
-        public MemoryJavaFileObject(String className, CharSequence sourceCode) {
-            super(URI.create("string:///" + className.replace('.','/') + Kind.SOURCE.extension), Kind.SOURCE);
-            this.className = className;
-            this.sourceCode = sourceCode;
-            this.byteCode = new ByteArrayOutputStream();
-        }
-
-        @Override
-        public CharSequence getCharContent(boolean ignoreEncodingErrors) {
-            return sourceCode;
-        }
-
-        @Override
-        public OutputStream openOutputStream() throws IOException {
-            return byteCode;
-        }
-
-        public byte[] getByteCode() {
-            return byteCode.toByteArray();
-        }
-
-        public String getClassName() {
-            return className;
-        }
-    }
-
-    private static class FileManagerWrapper extends ForwardingJavaFileManager {
-        private MemoryJavaFileObject file;
-
-        public FileManagerWrapper(MemoryJavaFileObject file) {
-            super(getCompiler().getStandardFileManager(null, null, null));
-            this.file = file;
-        }
-
-        @Override
-        public JavaFileObject getJavaFileForOutput(Location location, String className,
-                                                   Kind kind, FileObject sibling)
-            throws IOException {
-            if (!file.getClassName().equals(className)) {
-                throw new IOException("Expected class with name " + file.getClassName() +
-                                      ", but got " + className);
-            }
-            return file;
-        }
-    }
-
-    /**
-     * Compiles the class with the given name and source code.
-     *
-     * @param className The name of the class
-     * @param sourceCode The source code for the class with name {@code className}
-     * @throws RuntimeException if the compilation did not succeed
-     * @return The resulting byte code from the compilation
-     */
-    public static byte[] compile(String className, CharSequence sourceCode) {
-        MemoryJavaFileObject file = new MemoryJavaFileObject(className, sourceCode);
-        CompilationTask task = getCompilationTask(file);
-
-        if(!task.call()) {
-            throw new RuntimeException("Could not compile " + className + " with source code " + sourceCode);
-        }
-
-        return file.getByteCode();
-    }
-
-    private static JavaCompiler getCompiler() {
-        return ToolProvider.getSystemJavaCompiler();
-    }
-
-    private static CompilationTask getCompilationTask(MemoryJavaFileObject file) {
-        return getCompiler().getTask(null, new FileManagerWrapper(file), null, null, null, Arrays.asList(file));
-    }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/InfiniteLoop.java	Thu May 21 10:07:37 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.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package com.oracle.java.testlibrary;
-
-import java.util.Objects;
-
-/**
- * Class which runs another Runnable in infinite loop with certain pauses
- * between cycles.
- */
-public class InfiniteLoop implements Runnable {
-    private final Runnable target;
-    private final long mills;
-
-
-    /**
-     * @param target a target to run in a loop
-     * @param mills  the length of pause time in milliseconds
-     * @throws NullPointerException if target is null
-     * @throws IllegalArgumentException if the value of millis is negative
-     */
-    public InfiniteLoop(Runnable target, long mills) {
-        Objects.requireNonNull(target);
-        if (mills < 0) {
-            throw new IllegalArgumentException("mills < 0");
-        }
-        this.target = target;
-        this.mills = mills;
-    }
-
-    @Override
-    public void run() {
-        try {
-            while (true) {
-                target.run();
-                if (mills > 0) {
-                    Thread.sleep(mills);
-                }
-            }
-        } catch (InterruptedException e) {
-            Thread.currentThread().interrupt();
-            throw new Error(e);
-        }
-    }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/InputArguments.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,76 +0,0 @@
-/*
- * 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.
- */
-
-package com.oracle.java.testlibrary;
-
-import java.lang.management.RuntimeMXBean;
-import java.lang.management.ManagementFactory;
-import java.util.List;
-
-/**
- * This class provides access to the input arguments to the VM.
- */
-public class InputArguments {
-    private static final List<String> args;
-
-    static {
-        RuntimeMXBean runtimeMxBean = ManagementFactory.getRuntimeMXBean();
-        args = runtimeMxBean.getInputArguments();
-    }
-
-    /**
-     * Returns true if {@code arg} is an input argument to the VM.
-     *
-     * This is useful for checking boolean flags such as -XX:+UseSerialGC or
-     * -XX:-UsePerfData.
-     *
-     * @param arg The name of the argument.
-     * @return {@code true} if the given argument is an input argument,
-     *         otherwise {@code false}.
-     */
-    public static boolean contains(String arg) {
-        return args.contains(arg);
-    }
-
-    /**
-     * Returns true if {@code prefix} is the start of an input argument to the
-     * VM.
-     *
-     * This is useful for checking if flags describing a quantity, such as
-     * -XX:+MaxMetaspaceSize=100m, is set without having to know the quantity.
-     * To check if the flag -XX:MaxMetaspaceSize is set, use
-     * {@code InputArguments.containsPrefix("-XX:MaxMetaspaceSize")}.
-     *
-     * @param prefix The start of the argument.
-     * @return {@code true} if the given argument is the start of an input
-     *         argument, otherwise {@code false}.
-     */
-    public static boolean containsPrefix(String prefix) {
-        for (String arg : args) {
-            if (arg.startsWith(prefix)) {
-                return true;
-            }
-        }
-        return false;
-    }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/JDKToolFinder.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,106 +0,0 @@
-/*
- * 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.
- */
-
-package com.oracle.java.testlibrary;
-
-import java.io.FileNotFoundException;
-import java.nio.file.Path;
-import java.nio.file.Paths;
-
-public final class JDKToolFinder {
-
-    private JDKToolFinder() {
-    }
-
-    /**
-     * Returns the full path to an executable in jdk/bin based on System
-     * property {@code test.jdk} or {@code compile.jdk} (both are set by the jtreg test suite)
-     *
-     * @return Full path to an executable in jdk/bin
-     */
-    public static String getJDKTool(String tool) {
-
-        // First try to find the executable in test.jdk
-        try {
-            return getTool(tool, "test.jdk");
-        } catch (FileNotFoundException e) {
-
-        }
-
-        // Now see if it's available in compile.jdk
-        try {
-            return getTool(tool, "compile.jdk");
-        } catch (FileNotFoundException e) {
-            throw new RuntimeException("Failed to find " + tool +
-                    ", looked in test.jdk (" + System.getProperty("test.jdk") +
-                    ") and compile.jdk (" + System.getProperty("compile.jdk") + ")");
-        }
-    }
-
-    /**
-     * Returns the full path to an executable in jdk/bin based on System
-     * property {@code compile.jdk}
-     *
-     * @return Full path to an executable in jdk/bin
-     */
-    public static String getCompileJDKTool(String tool) {
-        try {
-            return getTool(tool, "compile.jdk");
-        } catch (FileNotFoundException e) {
-            throw new RuntimeException(e);
-        }
-    }
-
-    /**
-     * Returns the full path to an executable in jdk/bin based on System
-     * property {@code test.jdk}
-     *
-     * @return Full path to an executable in jdk/bin
-     */
-    public static String getTestJDKTool(String tool) {
-        try {
-            return getTool(tool, "test.jdk");
-        } catch (FileNotFoundException e) {
-            throw new RuntimeException(e);
-        }
-    }
-
-    private static String getTool(String tool, String property) throws FileNotFoundException {
-        String jdkPath = System.getProperty(property);
-
-        if (jdkPath == null) {
-            throw new RuntimeException(
-                    "System property '" + property + "' not set. This property is normally set by jtreg. "
-                    + "When running test separately, set this property using '-D" + property + "=/path/to/jdk'.");
-        }
-
-        Path toolName = Paths.get("bin", tool + (Platform.isWindows() ? ".exe" : ""));
-
-        Path jdkTool = Paths.get(jdkPath, toolName.toString());
-        if (!jdkTool.toFile().exists()) {
-            throw new FileNotFoundException("Could not find file " + jdkTool.toAbsolutePath());
-        }
-
-        return jdkTool.toAbsolutePath().toString();
-    }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/JDKToolLauncher.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,134 +0,0 @@
-/*
- * 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.
- */
-
-package com.oracle.java.testlibrary;
-
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.List;
-
-/**
- * A utility for constructing command lines for starting JDK tool processes.
- *
- * The JDKToolLauncher can in particular be combined with a
- * java.lang.ProcessBuilder to easily run a JDK tool. For example, the following
- * code run {@code jmap -heap} against a process with GC logging turned on for
- * the {@code jmap} process:
- *
- * <pre>
- * {@code
- * JDKToolLauncher jmap = JDKToolLauncher.create("jmap")
- *                                       .addVMArg("-XX:+PrintGC");
- *                                       .addVMArg("-XX:+PrintGCDetails")
- *                                       .addToolArg("-heap")
- *                                       .addToolArg(pid);
- * ProcessBuilder pb = new ProcessBuilder(jmap.getCommand());
- * Process p = pb.start();
- * }
- * </pre>
- */
-public class JDKToolLauncher {
-    private final String executable;
-    private final List<String> vmArgs = new ArrayList<String>();
-    private final List<String> toolArgs = new ArrayList<String>();
-
-    private JDKToolLauncher(String tool, boolean useCompilerJDK) {
-        if (useCompilerJDK) {
-            executable = JDKToolFinder.getJDKTool(tool);
-        } else {
-            executable = JDKToolFinder.getTestJDKTool(tool);
-        }
-        vmArgs.addAll(Arrays.asList(ProcessTools.getPlatformSpecificVMArgs()));
-    }
-
-    /**
-     * Creates a new JDKToolLauncher for the specified tool. Using tools path
-     * from the compiler JDK.
-     *
-     * @param tool
-     *            The name of the tool
-     * @return A new JDKToolLauncher
-     */
-    public static JDKToolLauncher create(String tool) {
-        return new JDKToolLauncher(tool, true);
-    }
-
-    /**
-     * Creates a new JDKToolLauncher for the specified tool in the Tested JDK.
-     *
-     * @param tool
-     *            The name of the tool
-     *
-     * @return A new JDKToolLauncher
-     */
-    public static JDKToolLauncher createUsingTestJDK(String tool) {
-        return new JDKToolLauncher(tool, false);
-    }
-
-    /**
-     * Adds an argument to the JVM running the tool.
-     *
-     * The JVM arguments are passed to the underlying JVM running the tool.
-     * Arguments will automatically be prepended with "-J".
-     *
-     * Any platform specific arguments required for running the tool are
-     * automatically added.
-     *
-     *
-     * @param arg
-     *            The argument to VM running the tool
-     * @return The JDKToolLauncher instance
-     */
-    public JDKToolLauncher addVMArg(String arg) {
-        vmArgs.add(arg);
-        return this;
-    }
-
-    /**
-     * Adds an argument to the tool.
-     *
-     * @param arg
-     *            The argument to the tool
-     * @return The JDKToolLauncher instance
-     */
-    public JDKToolLauncher addToolArg(String arg) {
-        toolArgs.add(arg);
-        return this;
-    }
-
-    /**
-     * Returns the command that can be used for running the tool.
-     *
-     * @return An array whose elements are the arguments of the command.
-     */
-    public String[] getCommand() {
-        List<String> command = new ArrayList<String>();
-        command.add(executable);
-        // Add -J in front of all vmArgs
-        for (String arg : vmArgs) {
-            command.add("-J" + arg);
-        }
-        command.addAll(toolArgs);
-        return command.toArray(new String[command.size()]);
-    }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/OutputAnalyzer.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,436 +0,0 @@
-/*
- * 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.
- */
-
-package com.oracle.java.testlibrary;
-
-import java.io.IOException;
-import java.util.Arrays;
-import java.util.List;
-import java.util.regex.Matcher;
-import java.util.regex.Pattern;
-
-public final class OutputAnalyzer {
-
-  private final String stdout;
-  private final String stderr;
-  private final int exitValue;
-
-  /**
-   * Create an OutputAnalyzer, a utility class for verifying output and exit
-   * value from a Process
-   *
-   * @param process Process to analyze
-   * @throws IOException If an I/O error occurs.
-   */
-  public OutputAnalyzer(Process process) throws IOException {
-    OutputBuffer output = ProcessTools.getOutput(process);
-    exitValue = process.exitValue();
-    this.stdout = output.getStdout();
-    this.stderr = output.getStderr();
-  }
-
-  /**
-   * Create an OutputAnalyzer, a utility class for verifying output
-   *
-   * @param buf String buffer to analyze
-   */
-  public OutputAnalyzer(String buf) {
-    this(buf, buf);
-  }
-
-  /**
-   * Create an OutputAnalyzer, a utility class for verifying output
-   *
-   * @param stdout stdout buffer to analyze
-   * @param stderr stderr buffer to analyze
-   */
-  public OutputAnalyzer(String stdout, String stderr) {
-    this.stdout = stdout;
-    this.stderr = stderr;
-    exitValue = -1;
-  }
-
-  /**
-   * Verify that the stdout contents of output buffer is empty
-   *
-   * @throws RuntimeException
-   *             If stdout was not empty
-   */
-  public void stdoutShouldBeEmpty() {
-    if (!getStdout().isEmpty()) {
-      reportDiagnosticSummary();
-      throw new RuntimeException("stdout was not empty");
-    }
-  }
-
-  /**
-   * Verify that the stderr contents of output buffer is empty
-   *
-   * @throws RuntimeException
-   *             If stderr was not empty
-   */
-  public void stderrShouldBeEmpty() {
-    if (!getStderr().isEmpty()) {
-      reportDiagnosticSummary();
-      throw new RuntimeException("stderr was not empty");
-    }
-  }
-
-  /**
-   * Verify that the stdout contents of output buffer is not empty
-   *
-   * @throws RuntimeException
-   *             If stdout was empty
-   */
-  public void stdoutShouldNotBeEmpty() {
-    if (getStdout().isEmpty()) {
-      reportDiagnosticSummary();
-      throw new RuntimeException("stdout was empty");
-    }
-  }
-
-  /**
-   * Verify that the stderr contents of output buffer is not empty
-   *
-   * @throws RuntimeException
-   *             If stderr was empty
-   */
-  public void stderrShouldNotBeEmpty() {
-    if (getStderr().isEmpty()) {
-      reportDiagnosticSummary();
-      throw new RuntimeException("stderr was empty");
-    }
-  }
-
-    /**
-   * Verify that the stdout and stderr contents of output buffer contains the string
-   *
-   * @param expectedString String that buffer should contain
-   * @throws RuntimeException If the string was not found
-   */
-  public OutputAnalyzer shouldContain(String expectedString) {
-    if (!stdout.contains(expectedString) && !stderr.contains(expectedString)) {
-        reportDiagnosticSummary();
-        throw new RuntimeException("'" + expectedString + "' missing from stdout/stderr \n");
-    }
-    return this;
-  }
-
-  /**
-   * Verify that the stdout contents of output buffer contains the string
-   *
-   * @param expectedString String that buffer should contain
-   * @throws RuntimeException If the string was not found
-   */
-  public OutputAnalyzer stdoutShouldContain(String expectedString) {
-    if (!stdout.contains(expectedString)) {
-        reportDiagnosticSummary();
-        throw new RuntimeException("'" + expectedString + "' missing from stdout \n");
-    }
-    return this;
-  }
-
-  /**
-   * Verify that the stderr contents of output buffer contains the string
-   *
-   * @param expectedString String that buffer should contain
-   * @throws RuntimeException If the string was not found
-   */
-  public OutputAnalyzer stderrShouldContain(String expectedString) {
-    if (!stderr.contains(expectedString)) {
-        reportDiagnosticSummary();
-        throw new RuntimeException("'" + expectedString + "' missing from stderr \n");
-    }
-    return this;
-  }
-
-  /**
-   * Verify that the stdout and stderr contents of output buffer does not contain the string
-   *
-   * @param expectedString String that the buffer should not contain
-   * @throws RuntimeException If the string was found
-   */
-  public OutputAnalyzer shouldNotContain(String notExpectedString) {
-    if (stdout.contains(notExpectedString)) {
-        reportDiagnosticSummary();
-        throw new RuntimeException("'" + notExpectedString + "' found in stdout \n");
-    }
-    if (stderr.contains(notExpectedString)) {
-        reportDiagnosticSummary();
-        throw new RuntimeException("'" + notExpectedString + "' found in stderr \n");
-    }
-    return this;
-  }
-
-  /**
-   * Verify that the stdout contents of output buffer does not contain the string
-   *
-   * @param expectedString String that the buffer should not contain
-   * @throws RuntimeException If the string was found
-   */
-  public OutputAnalyzer stdoutShouldNotContain(String notExpectedString) {
-    if (stdout.contains(notExpectedString)) {
-        reportDiagnosticSummary();
-        throw new RuntimeException("'" + notExpectedString + "' found in stdout \n");
-    }
-    return this;
-  }
-
-  /**
-   * Verify that the stderr contents of output buffer does not contain the string
-   *
-   * @param expectedString String that the buffer should not contain
-   * @throws RuntimeException If the string was found
-   */
-  public OutputAnalyzer stderrShouldNotContain(String notExpectedString) {
-    if (stderr.contains(notExpectedString)) {
-        reportDiagnosticSummary();
-        throw new RuntimeException("'" + notExpectedString + "' found in stderr \n");
-    }
-    return this;
-  }
-
-  /**
-   * Verify that the stdout and stderr contents of output buffer matches
-   * the pattern
-   *
-   * @param pattern
-   * @throws RuntimeException If the pattern was not found
-   */
-  public OutputAnalyzer shouldMatch(String pattern) {
-      Matcher stdoutMatcher = Pattern.compile(pattern, Pattern.MULTILINE).matcher(stdout);
-      Matcher stderrMatcher = Pattern.compile(pattern, Pattern.MULTILINE).matcher(stderr);
-      if (!stdoutMatcher.find() && !stderrMatcher.find()) {
-          reportDiagnosticSummary();
-          throw new RuntimeException("'" + pattern
-                + "' missing from stdout/stderr \n");
-      }
-      return this;
-  }
-
-  /**
-   * Verify that the stdout contents of output buffer matches the
-   * pattern
-   *
-   * @param pattern
-   * @throws RuntimeException If the pattern was not found
-   */
-  public OutputAnalyzer stdoutShouldMatch(String pattern) {
-      Matcher matcher = Pattern.compile(pattern, Pattern.MULTILINE).matcher(stdout);
-      if (!matcher.find()) {
-          reportDiagnosticSummary();
-          throw new RuntimeException("'" + pattern
-                + "' missing from stdout \n");
-      }
-      return this;
-  }
-
-  /**
-   * Verify that the stderr contents of output buffer matches the
-   * pattern
-   *
-   * @param pattern
-   * @throws RuntimeException If the pattern was not found
-   */
-  public OutputAnalyzer stderrShouldMatch(String pattern) {
-      Matcher matcher = Pattern.compile(pattern, Pattern.MULTILINE).matcher(stderr);
-      if (!matcher.find()) {
-          reportDiagnosticSummary();
-          throw new RuntimeException("'" + pattern
-                + "' missing from stderr \n");
-      }
-      return this;
-  }
-
-  /**
-   * Verify that the stdout and stderr contents of output buffer does not
-   * match the pattern
-   *
-   * @param pattern
-   * @throws RuntimeException If the pattern was found
-   */
-  public OutputAnalyzer shouldNotMatch(String pattern) {
-      Matcher matcher = Pattern.compile(pattern, Pattern.MULTILINE).matcher(stdout);
-      if (matcher.find()) {
-          reportDiagnosticSummary();
-          throw new RuntimeException("'" + pattern
-                  + "' found in stdout: '" + matcher.group() + "' \n");
-      }
-      matcher = Pattern.compile(pattern, Pattern.MULTILINE).matcher(stderr);
-      if (matcher.find()) {
-          reportDiagnosticSummary();
-          throw new RuntimeException("'" + pattern
-                  + "' found in stderr: '" + matcher.group() + "' \n");
-      }
-      return this;
-  }
-
-  /**
-   * Verify that the stdout contents of output buffer does not match the
-   * pattern
-   *
-   * @param pattern
-   * @throws RuntimeException If the pattern was found
-   */
-  public OutputAnalyzer stdoutShouldNotMatch(String pattern) {
-      Matcher matcher = Pattern.compile(pattern, Pattern.MULTILINE).matcher(stdout);
-      if (matcher.find()) {
-          reportDiagnosticSummary();
-          throw new RuntimeException("'" + pattern
-                  + "' found in stdout \n");
-      }
-      return this;
-  }
-
-  /**
-   * Verify that the stderr contents of output buffer does not match the
-   * pattern
-   *
-   * @param pattern
-   * @throws RuntimeException If the pattern was found
-   */
-  public OutputAnalyzer stderrShouldNotMatch(String pattern) {
-      Matcher matcher = Pattern.compile(pattern, Pattern.MULTILINE).matcher(stderr);
-      if (matcher.find()) {
-          reportDiagnosticSummary();
-          throw new RuntimeException("'" + pattern
-                  + "' found in stderr \n");
-      }
-      return this;
-  }
-
-  /**
-   * Get the captured group of the first string matching the pattern.
-   * stderr is searched before stdout.
-   *
-   * @param pattern The multi-line pattern to match
-   * @param group The group to capture
-   * @return The matched string or null if no match was found
-   */
-  public String firstMatch(String pattern, int group) {
-    Matcher stderrMatcher = Pattern.compile(pattern, Pattern.MULTILINE).matcher(stderr);
-    Matcher stdoutMatcher = Pattern.compile(pattern, Pattern.MULTILINE).matcher(stdout);
-    if (stderrMatcher.find()) {
-      return stderrMatcher.group(group);
-    }
-    if (stdoutMatcher.find()) {
-      return stdoutMatcher.group(group);
-    }
-    return null;
-  }
-
-  /**
-   * Get the first string matching the pattern.
-   * stderr is searched before stdout.
-   *
-   * @param pattern The multi-line pattern to match
-   * @return The matched string or null if no match was found
-   */
-  public String firstMatch(String pattern) {
-    return firstMatch(pattern, 0);
-  }
-
-  /**
-   * Verify the exit value of the process
-   *
-   * @param expectedExitValue Expected exit value from process
-   * @throws RuntimeException If the exit value from the process did not match the expected value
-   */
-  public OutputAnalyzer shouldHaveExitValue(int expectedExitValue) {
-      if (getExitValue() != expectedExitValue) {
-          reportDiagnosticSummary();
-          throw new RuntimeException("Expected to get exit value of ["
-                  + expectedExitValue + "]\n");
-      }
-      return this;
-  }
-
-
-  /**
-   * Report summary that will help to diagnose the problem
-   * Currently includes:
-   *  - standard input produced by the process under test
-   *  - standard output
-   *  - exit code
-   *  Note: the command line is printed by the ProcessTools
-   */
-    private void reportDiagnosticSummary() {
-        String msg =
-            " stdout: [" + stdout + "];\n" +
-            " stderr: [" + stderr + "]\n" +
-            " exitValue = " + getExitValue() + "\n";
-
-        System.err.println(msg);
-    }
-
-
-  /**
-   * Get the contents of the output buffer (stdout and stderr)
-   *
-   * @return Content of the output buffer
-   */
-  public String getOutput() {
-    return stdout + stderr;
-  }
-
-  /**
-   * Get the contents of the stdout buffer
-   *
-   * @return Content of the stdout buffer
-   */
-  public String getStdout() {
-    return stdout;
-  }
-
-  /**
-   * Get the contents of the stderr buffer
-   *
-   * @return Content of the stderr buffer
-   */
-  public String getStderr() {
-    return stderr;
-  }
-
-  /**
-   * Get the process exit value
-   *
-   * @return Process exit value
-   */
-  public int getExitValue() {
-    return exitValue;
-  }
-
-  /**
-   * Get the contents of the output buffer (stdout and stderr) as list of strings.
-   * Output will be split by newlines.
-   *
-   * @return Contents of the output buffer as list of strings
-   */
-  public List<String> asLines() {
-    return asLines(getOutput());
-  }
-
-  private List<String> asLines(String buffer) {
-    return Arrays.asList(buffer.split("(\\r\\n|\\n|\\r)"));
-  }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/OutputBuffer.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,59 +0,0 @@
-/*
- * 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.
- */
-
-package com.oracle.java.testlibrary;
-
-public class OutputBuffer {
-  private final String stdout;
-  private final String stderr;
-
-  /**
-   * Create an OutputBuffer, a class for storing and managing stdout and stderr
-   * results separately
-   *
-   * @param stdout stdout result
-   * @param stderr stderr result
-   */
-  public OutputBuffer(String stdout, String stderr) {
-    this.stdout = stdout;
-    this.stderr = stderr;
-  }
-
-  /**
-   * Returns the stdout result
-   *
-   * @return stdout result
-   */
-  public String getStdout() {
-    return stdout;
-  }
-
-  /**
-   * Returns the stderr result
-   *
-   * @return stderr result
-   */
-  public String getStderr() {
-    return stderr;
-  }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/PerfCounter.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,70 +0,0 @@
-/*
- * 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.
- */
-
-package com.oracle.java.testlibrary;
-
-import sun.jvmstat.monitor.Monitor;
-
-/**
- * Represents a performance counter in the JVM.
- *
- * See http://openjdk.java.net/groups/hotspot/docs/Serviceability.html#bjvmstat
- * for more details about performance counters.
- */
-public class PerfCounter {
-    private final Monitor monitor;
-    private final String name;
-
-    PerfCounter(Monitor monitor, String name) {
-        this.monitor = monitor;
-        this.name = name;
-    }
-
-    /**
-     * Returns the value of this performance counter as a long.
-     *
-     * @return The long value of this performance counter
-     * @throws RuntimeException If the value of the performance counter isn't a long
-     */
-    public long longValue() {
-        Object value = monitor.getValue();
-        if (value instanceof Long) {
-            return ((Long) value).longValue();
-        }
-        throw new RuntimeException("Expected " + monitor.getName() + " to have a long value");
-    }
-
-    /**
-     * Returns the name of the performance counter.
-     *
-     * @return The name of the performance counter.
-     */
-    public String getName() {
-        return name;
-    }
-
-    @Override
-    public String toString() {
-        return name;
-    }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/PerfCounters.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,69 +0,0 @@
-/*
- * 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.
- */
-
-package com.oracle.java.testlibrary;
-
-import sun.jvmstat.monitor.Monitor;
-import sun.jvmstat.monitor.MonitorException;
-import sun.jvmstat.monitor.MonitoredHost;
-import sun.jvmstat.monitor.MonitoredVm;
-import sun.jvmstat.monitor.VmIdentifier;
-
-/**
- * PerfCounters can be used to get a performance counter from the currently
- * executing VM.
- *
- * Throws a runtime exception if an error occurs while communicating with the
- * currently executing VM.
- */
-public class PerfCounters {
-    private final static MonitoredVm vm;
-
-    static {
-        try {
-            String pid = Integer.toString(ProcessTools.getProcessId());
-            VmIdentifier vmId = new VmIdentifier(pid);
-            MonitoredHost host = MonitoredHost.getMonitoredHost(vmId);
-            vm = host.getMonitoredVm(vmId);
-        } catch (Exception e) {
-            throw new RuntimeException("Could not connect to the VM");
-        }
-    }
-
-    /**
-     * Returns the performance counter with the given name.
-     *
-     * @param name The name of the performance counter.
-     * @throws IllegalArgumentException If no counter with the given name exists.
-     * @throws MonitorException If an error occurs while communicating with the VM.
-     * @return The performance counter with the given name.
-     */
-    public static PerfCounter findByName(String name)
-        throws MonitorException, IllegalArgumentException {
-        Monitor m = vm.findByName(name);
-        if (m == null) {
-            throw new IllegalArgumentException("Did not find a performance counter with name " + name);
-        }
-        return new PerfCounter(m, name);
-    }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/Platform.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,199 +0,0 @@
-/*
- * 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
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package com.oracle.java.testlibrary;
-
-import java.util.regex.Pattern;
-import com.oracle.java.testlibrary.Utils;
-
-public class Platform {
-    private static final String osName      = System.getProperty("os.name");
-    private static final String dataModel   = System.getProperty("sun.arch.data.model");
-    private static final String vmVersion   = System.getProperty("java.vm.version");
-    private static final String javaVersion = System.getProperty("java.version");
-    private static final String osArch      = System.getProperty("os.arch");
-    private static final String vmName      = System.getProperty("java.vm.name");
-    private static final String userName    = System.getProperty("user.name");
-    private static final String compiler    = System.getProperty("sun.management.compiler");
-
-    public static boolean isClient() {
-        return vmName.endsWith(" Client VM");
-    }
-
-    public static boolean isServer() {
-        return vmName.endsWith(" Server VM");
-    }
-
-    public static boolean isGraal() {
-        return vmName.endsWith(" Graal VM");
-    }
-
-    public static boolean isZero() {
-        return vmName.endsWith(" Zero VM");
-    }
-
-    public static boolean isMinimal() {
-        return vmName.endsWith(" Minimal VM");
-    }
-
-    public static boolean isEmbedded() {
-        return vmName.contains("Embedded");
-    }
-
-    public static boolean isTieredSupported() {
-        return compiler.contains("Tiered Compilers");
-    }
-
-    public static boolean is32bit() {
-        return dataModel.equals("32");
-    }
-
-    public static boolean is64bit() {
-        return dataModel.equals("64");
-    }
-
-    public static boolean isAix() {
-        return isOs("aix");
-    }
-
-    public static boolean isLinux() {
-        return isOs("linux");
-    }
-
-    public static boolean isOSX() {
-        return isOs("mac");
-    }
-
-    public static boolean isSolaris() {
-        return isOs("sunos");
-    }
-
-    public static boolean isWindows() {
-        return isOs("win");
-    }
-
-    private static boolean isOs(String osname) {
-        return osName.toLowerCase().startsWith(osname.toLowerCase());
-    }
-
-    public static String getOsName() {
-        return osName;
-    }
-
-    public static boolean isDebugBuild() {
-        return (vmVersion.toLowerCase().contains("debug") ||
-                javaVersion.toLowerCase().contains("debug"));
-    }
-
-    public static String getVMVersion() {
-        return vmVersion;
-    }
-
-    // Returns true for sparc and sparcv9.
-    public static boolean isSparc() {
-        return isArch("sparc.*");
-    }
-
-    public static boolean isARM() {
-        return isArch("arm.*");
-    }
-
-    public static boolean isPPC() {
-        return isArch("ppc.*");
-    }
-
-    public static boolean isX86() {
-        // On Linux it's 'i386', Windows 'x86' without '_64' suffix.
-        return isArch("(i386)|(x86(?!_64))");
-    }
-
-    public static boolean isX64() {
-        // On OSX it's 'x86_64' and on other (Linux, Windows and Solaris) platforms it's 'amd64'
-        return isArch("(amd64)|(x86_64)");
-    }
-
-    private static boolean isArch(String archnameRE) {
-        return Pattern.compile(archnameRE, Pattern.CASE_INSENSITIVE)
-                .matcher(osArch)
-                .matches();
-    }
-
-    public static String getOsArch() {
-        return osArch;
-    }
-
-    /**
-     * Return a boolean for whether we expect to be able to attach
-     * the SA to our own processes on this system.
-     */
-    public static boolean shouldSAAttach() throws Exception {
-
-        if (isAix()) {
-            return false;   // SA not implemented.
-        } else if (isLinux()) {
-            return canPtraceAttachLinux();
-        } else if (isOSX()) {
-            return canAttachOSX();
-        } else {
-            // Other platforms expected to work:
-            return true;
-        }
-    }
-
-    /**
-     * On Linux, first check the SELinux boolean "deny_ptrace" and return false
-     * as we expect to be denied if that is "1".  Then expect permission to attach
-     * if we are root, so return true.  Then return false for an expected denial
-     * if "ptrace_scope" is 1, and true otherwise.
-     */
-    public static boolean canPtraceAttachLinux() throws Exception {
-
-        // SELinux deny_ptrace:
-        String deny_ptrace = Utils.fileAsString("/sys/fs/selinux/booleans/deny_ptrace");
-        if (deny_ptrace != null && deny_ptrace.contains("1")) {
-            // ptrace will be denied:
-            return false;
-        }
-
-        if (userName.equals("root")) {
-            return true;
-        }
-
-        // ptrace_scope:
-        String ptrace_scope = Utils.fileAsString("/proc/sys/kernel/yama/ptrace_scope");
-        if (ptrace_scope != null && ptrace_scope.contains("1")) {
-            // ptrace will be denied:
-            return false;
-        }
-
-        // Otherwise expect to be permitted:
-        return true;
-    }
-
-    /**
-     * On OSX, expect permission to attach only if we are root.
-     */
-    public static boolean canAttachOSX() throws Exception {
-        return userName.equals("root");
-    }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/ProcessTools.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,249 +0,0 @@
-/*
- * 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.
- */
-
-package com.oracle.java.testlibrary;
-
-import java.io.ByteArrayOutputStream;
-import java.io.IOException;
-import java.lang.management.ManagementFactory;
-import java.lang.management.RuntimeMXBean;
-import java.lang.reflect.Field;
-import java.lang.reflect.Method;
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.List;
-
-public final class ProcessTools {
-
-  private ProcessTools() {
-  }
-
-  /**
-   * Pumps stdout and stderr from running the process into a String.
-   *
-   * @param processHandler ProcessHandler to run.
-   * @return Output from process.
-   * @throws IOException If an I/O error occurs.
-   */
-  public static OutputBuffer getOutput(ProcessBuilder processBuilder) throws IOException {
-    return getOutput(processBuilder.start());
-  }
-
-  /**
-   * Pumps stdout and stderr the running process into a String.
-   *
-   * @param process Process to pump.
-   * @return Output from process.
-   * @throws IOException If an I/O error occurs.
-   */
-  public static OutputBuffer getOutput(Process process) throws IOException {
-    ByteArrayOutputStream stderrBuffer = new ByteArrayOutputStream();
-    ByteArrayOutputStream stdoutBuffer = new ByteArrayOutputStream();
-    StreamPumper outPumper = new StreamPumper(process.getInputStream(), stdoutBuffer);
-    StreamPumper errPumper = new StreamPumper(process.getErrorStream(), stderrBuffer);
-    Thread outPumperThread = new Thread(outPumper);
-    Thread errPumperThread = new Thread(errPumper);
-
-    outPumperThread.setDaemon(true);
-    errPumperThread.setDaemon(true);
-
-    outPumperThread.start();
-    errPumperThread.start();
-
-    try {
-      process.waitFor();
-      outPumperThread.join();
-      errPumperThread.join();
-    } catch (InterruptedException e) {
-      Thread.currentThread().interrupt();
-      return null;
-    }
-
-    return new OutputBuffer(stdoutBuffer.toString(), stderrBuffer.toString());
-  }
-
-  /**
-   * Get the process id of the current running Java process
-   *
-   * @return Process id
-   */
-  public static int getProcessId() throws Exception {
-    RuntimeMXBean runtime = ManagementFactory.getRuntimeMXBean();
-    int pid = Integer.parseInt(runtime.getName().split("@")[0]);
-
-    return pid;
-  }
-
-  /**
-   * Get the string containing input arguments passed to the VM
-   *
-   * @return arguments
-   */
-  public static String getVmInputArguments() {
-    RuntimeMXBean runtime = ManagementFactory.getRuntimeMXBean();
-
-    List<String> args = runtime.getInputArguments();
-    StringBuilder result = new StringBuilder();
-    for (String arg : args)
-        result.append(arg).append(' ');
-
-    return result.toString();
-  }
-
-  /**
-   * Get platform specific VM arguments (e.g. -d64 on 64bit Solaris)
-   *
-   * @return String[] with platform specific arguments, empty if there are none
-   */
-  public static String[] getPlatformSpecificVMArgs() {
-
-    if (Platform.is64bit() && Platform.isSolaris()) {
-      return new String[] { "-d64" };
-    }
-
-    return new String[] {};
-  }
-
-  /**
-   * Create ProcessBuilder using the java launcher from the jdk to be tested and
-   * with any platform specific arguments prepended
-   */
-  public static ProcessBuilder createJavaProcessBuilder(String... command) throws Exception {
-    return createJavaProcessBuilder(false, command);
-  }
-
-  public static ProcessBuilder createJavaProcessBuilder(boolean addTestVmAndJavaOptions, String... command) throws Exception {
-    String javapath = JDKToolFinder.getJDKTool("java");
-
-    ArrayList<String> args = new ArrayList<>();
-    args.add(javapath);
-    Collections.addAll(args, getPlatformSpecificVMArgs());
-
-    args.add("-cp");
-    args.add(System.getProperty("java.class.path"));
-
-    if (addTestVmAndJavaOptions) {
-      Collections.addAll(args, Utils.getTestJavaOpts());
-    }
-
-    Collections.addAll(args, command);
-
-    // Reporting
-    StringBuilder cmdLine = new StringBuilder();
-    for (String cmd : args) {
-      cmdLine.append(cmd).append(' ');
-    }
-    System.out.println("Command line: [" + cmdLine.toString() + "]");
-
-    return new ProcessBuilder(args.toArray(new String[args.size()]));
-  }
-
-  /**
-   * Executes a test jvm process, waits for it to finish and returns the process output.
-   * The default jvm options from jtreg, test.vm.opts and test.java.opts, are added.
-   * The java from the test.jdk is used to execute the command.
-   *
-   * The command line will be like:
-   * {test.jdk}/bin/java {test.vm.opts} {test.java.opts} cmds
-   *
-   * @param cmds User specifed arguments.
-   * @return The output from the process.
-   */
-  public static OutputAnalyzer executeTestJvm(String... cmds) throws Throwable {
-    ProcessBuilder pb = createJavaProcessBuilder(Utils.addTestJavaOpts(cmds));
-    return executeProcess(pb);
-  }
-
-    /**
-     * Executes a process, waits for it to finish and returns the process output.
-     * The process will have exited before this method returns.
-     * @param pb The ProcessBuilder to execute.
-     * @return The {@linkplain OutputAnalyzer} instance wrapping the process.
-     */
-    public static OutputAnalyzer executeProcess(ProcessBuilder pb) throws Exception {
-        OutputAnalyzer output = null;
-        Process p = null;
-        boolean failed = false;
-        try {
-            p = pb.start();
-            output = new OutputAnalyzer(p);
-            p.waitFor();
-
-            return output;
-        } catch (Throwable t) {
-            if (p != null) {
-                p.destroyForcibly().waitFor();
-            }
-
-            failed = true;
-            System.out.println("executeProcess() failed: " + t);
-            throw t;
-        } finally {
-            if (failed) {
-                System.err.println(getProcessLog(pb, output));
-            }
-        }
-    }
-
-  /**
-   * Executes a process, waits for it to finish and returns the process output.
-   * @param cmds The command line to execute.
-   * @return The output from the process.
-   */
-  public static OutputAnalyzer executeProcess(String... cmds) throws Throwable {
-    return executeProcess(new ProcessBuilder(cmds));
-  }
-
-  /**
-   * Used to log command line, stdout, stderr and exit code from an executed process.
-   * @param pb The executed process.
-   * @param output The output from the process.
-   */
-  public static String getProcessLog(ProcessBuilder pb, OutputAnalyzer output) {
-    String stderr = output == null ? "null" : output.getStderr();
-    String stdout = output == null ? "null" : output.getStdout();
-    String exitValue = output == null ? "null": Integer.toString(output.getExitValue());
-    StringBuilder logMsg = new StringBuilder();
-    final String nl = System.getProperty("line.separator");
-    logMsg.append("--- ProcessLog ---" + nl);
-    logMsg.append("cmd: " + getCommandLine(pb) + nl);
-    logMsg.append("exitvalue: " + exitValue + nl);
-    logMsg.append("stderr: " + stderr + nl);
-    logMsg.append("stdout: " + stdout + nl);
-    return logMsg.toString();
-  }
-
-  /**
-   * @return The full command line for the ProcessBuilder.
-   */
-  public static String getCommandLine(ProcessBuilder pb) {
-    if (pb == null) {
-      return "null";
-    }
-    StringBuilder cmd = new StringBuilder();
-    for (String s : pb.command()) {
-      cmd.append(s).append(" ");
-    }
-    return cmd.toString().trim();
-  }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/StreamPumper.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,76 +0,0 @@
-/*
- * 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.
- */
-
-package com.oracle.java.testlibrary;
-
-import java.io.OutputStream;
-import java.io.InputStream;
-import java.io.IOException;
-
-public final class StreamPumper implements Runnable {
-
-  private static final int BUF_SIZE = 256;
-
-  private final OutputStream out;
-  private final InputStream in;
-
-  /**
-   * Create a StreamPumper that reads from in and writes to out.
-   *
-   * @param in The stream to read from.
-   * @param out The stream to write to.
-   */
-  public StreamPumper(InputStream in, OutputStream out) {
-    this.in = in;
-    this.out = out;
-  }
-
-  /**
-   * Implements Thread.run(). Continuously read from <code>in</code> and write
-   * to <code>out</code> until <code>in</code> has reached end of stream. Abort
-   * on interruption. Abort on IOExceptions.
-   */
-  @Override
-  public void run() {
-    int length;
-    InputStream localIn = in;
-    OutputStream localOut = out;
-    byte[] buffer = new byte[BUF_SIZE];
-
-    try {
-      while (!Thread.interrupted() && (length = localIn.read(buffer)) > 0) {
-        localOut.write(buffer, 0, length);
-      }
-    } catch (IOException e) {
-      // Just abort if something like this happens.
-      e.printStackTrace();
-    } finally {
-      try {
-        localOut.flush();
-        in.close();
-      } catch (IOException e) {
-        e.printStackTrace();
-      }
-    }
-  }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/TimeLimitedRunner.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,86 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package com.oracle.java.testlibrary;
-
-import java.util.Objects;
-import java.util.concurrent.Callable;
-
-/**
- * Auxiliary class to run target w/ given timeout.
- */
-public class TimeLimitedRunner implements Callable<Void> {
-    private final long              stoptime;
-    private final long              timeout;
-    private final double            factor;
-    private final Callable<Boolean> target;
-
-    /**
-     * @param timeout   a timeout. zero means no time limitation
-     * @param factor    a multiplier used to estimate next iteration time
-     * @param target    a target to run
-     * @throws NullPointerException     if target is null
-     * @throws IllegalArgumentException if timeout is negative or
-                                        factor isn't positive
-     */
-    public TimeLimitedRunner(long timeout, double factor,
-            Callable<Boolean> target) {
-        Objects.requireNonNull(target, "target must not be null");
-        if (timeout < 0) {
-            throw new IllegalArgumentException("timeout[" + timeout + "] < 0");
-        }
-        if (factor <= 0d) {
-            throw new IllegalArgumentException("factor[" + factor + "] <= 0");
-        }
-        this.stoptime = System.currentTimeMillis() + timeout;
-        this.timeout = timeout;
-        this.factor = factor;
-        this.target = target;
-    }
-
-    /**
-     * Runs @{linkplan target} while it returns true and timeout isn't exceeded
-     */
-    @Override
-    public Void call() throws Exception {
-        long maxDuration = 0L;
-        long iterStart = System.currentTimeMillis();
-        if (timeout != 0 && iterStart > stoptime) {
-            return null;
-        }
-        while (target.call()) {
-            if (timeout != 0) {
-                long iterDuration = System.currentTimeMillis() - iterStart;
-                maxDuration = Math.max(maxDuration, iterDuration);
-                iterStart = System.currentTimeMillis();
-                if (iterStart + (maxDuration * factor) > stoptime) {
-                    System.out.println("Not enough time to continue execution. "
-                            + "Interrupted.");
-                    break;
-                }
-            }
-        }
-        return null;
-    }
-
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/Utils.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,435 +0,0 @@
-/*
- * Copyright (c) 2013, 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package com.oracle.java.testlibrary;
-
-import static com.oracle.java.testlibrary.Asserts.assertTrue;
-import java.io.BufferedReader;
-import java.io.File;
-import java.io.FileReader;
-import java.io.IOException;
-import java.lang.reflect.Field;
-import java.net.InetAddress;
-import java.net.ServerSocket;
-import java.net.UnknownHostException;
-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.Collections;
-import java.util.List;
-import java.util.Random;
-import java.util.function.BooleanSupplier;
-import java.util.concurrent.TimeUnit;
-import java.util.regex.Matcher;
-import java.util.regex.Pattern;
-import java.util.stream.Collectors;
-import sun.misc.Unsafe;
-
-/**
- * Common library for various test helper functions.
- */
-public final class Utils {
-
-    /**
-     * Returns the sequence used by operating system to separate lines.
-     */
-    public static final String NEW_LINE = System.getProperty("line.separator");
-
-    /**
-     * Returns the value of 'test.vm.opts'system property.
-     */
-    public static final String VM_OPTIONS = System.getProperty("test.vm.opts", "").trim();
-
-    /**
-     * Returns the value of 'test.java.opts'system property.
-     */
-    public static final String JAVA_OPTIONS = System.getProperty("test.java.opts", "").trim();
-
-    private static Unsafe unsafe = null;
-
-    /**
-     * Defines property name for seed value.
-     */
-    public static final String SEED_PROPERTY_NAME = "com.oracle.java.testlibrary.random.seed";
-
-    /* (non-javadoc)
-     * Random generator with (or without) predefined seed. Depends on
-     * "com.oracle.java.testlibrary.random.seed" property value.
-     */
-    private static volatile Random RANDOM_GENERATOR;
-
-    /**
-     * Contains the seed value used for {@link java.util.Random} creation.
-     */
-    public static final long SEED = Long.getLong(SEED_PROPERTY_NAME, new Random().nextLong());
-    /**
-    * Returns the value of 'test.timeout.factor' system property
-    * converted to {@code double}.
-    */
-    public static final double TIMEOUT_FACTOR;
-    static {
-        String toFactor = System.getProperty("test.timeout.factor", "1.0");
-        TIMEOUT_FACTOR = Double.parseDouble(toFactor);
-    }
-
-    /**
-    * Returns the value of JTREG default test timeout in milliseconds
-    * converted to {@code long}.
-    */
-    public static final long DEFAULT_TEST_TIMEOUT = TimeUnit.SECONDS.toMillis(120);
-
-    private Utils() {
-        // Private constructor to prevent class instantiation
-    }
-
-    /**
-     * Returns the list of VM options.
-     *
-     * @return List of VM options
-     */
-    public static List<String> getVmOptions() {
-        return Arrays.asList(safeSplitString(VM_OPTIONS));
-    }
-
-    /**
-     * Returns the list of VM options with -J prefix.
-     *
-     * @return The list of VM options with -J prefix
-     */
-    public static List<String> getForwardVmOptions() {
-        String[] opts = safeSplitString(VM_OPTIONS);
-        for (int i = 0; i < opts.length; i++) {
-            opts[i] = "-J" + opts[i];
-        }
-        return Arrays.asList(opts);
-    }
-
-    /**
-     * Returns the default JTReg arguments for a jvm running a test.
-     * This is the combination of JTReg arguments test.vm.opts and test.java.opts.
-     * @return An array of options, or an empty array if no opptions.
-     */
-    public static String[] getTestJavaOpts() {
-        List<String> opts = new ArrayList<String>();
-        Collections.addAll(opts, safeSplitString(VM_OPTIONS));
-        Collections.addAll(opts, safeSplitString(JAVA_OPTIONS));
-        return opts.toArray(new String[0]);
-    }
-
-    /**
-     * Returns the default JTReg arguments for a jvm running a test without
-     * options that matches regular expressions in {@code filters}.
-     * This is the combination of JTReg arguments test.vm.opts and test.java.opts.
-     * @param filters Regular expressions used to filter out options.
-     * @return An array of options, or an empty array if no options.
-     */
-    public static String[] getFilteredTestJavaOpts(String... filters) {
-        String options[] = getTestJavaOpts();
-
-        if (filters.length == 0) {
-            return options;
-        }
-
-        List<String> filteredOptions = new ArrayList<String>(options.length);
-        Pattern patterns[] = new Pattern[filters.length];
-        for (int i = 0; i < filters.length; i++) {
-            patterns[i] = Pattern.compile(filters[i]);
-        }
-
-        for (String option : options) {
-            boolean matched = false;
-            for (int i = 0; i < patterns.length && !matched; i++) {
-                Matcher matcher = patterns[i].matcher(option);
-                matched = matcher.find();
-            }
-            if (!matched) {
-                filteredOptions.add(option);
-            }
-        }
-
-        return filteredOptions.toArray(new String[filteredOptions.size()]);
-    }
-
-    /**
-     * Combines given arguments with default JTReg arguments for a jvm running a test.
-     * This is the combination of JTReg arguments test.vm.opts and test.java.opts
-     * @return The combination of JTReg test java options and user args.
-     */
-    public static String[] addTestJavaOpts(String... userArgs) {
-        List<String> opts = new ArrayList<String>();
-        Collections.addAll(opts, getTestJavaOpts());
-        Collections.addAll(opts, userArgs);
-        return opts.toArray(new String[0]);
-    }
-
-    /**
-     * Splits a string by white space.
-     * Works like String.split(), but returns an empty array
-     * if the string is null or empty.
-     */
-    private static String[] safeSplitString(String s) {
-        if (s == null || s.trim().isEmpty()) {
-            return new String[] {};
-        }
-        return s.trim().split("\\s+");
-    }
-
-    /**
-     * @return The full command line for the ProcessBuilder.
-     */
-    public static String getCommandLine(ProcessBuilder pb) {
-        StringBuilder cmd = new StringBuilder();
-        for (String s : pb.command()) {
-            cmd.append(s).append(" ");
-        }
-        return cmd.toString();
-    }
-
-    /**
-     * Returns the free port on the local host.
-     * The function will spin until a valid port number is found.
-     *
-     * @return The port number
-     * @throws InterruptedException if any thread has interrupted the current thread
-     * @throws IOException if an I/O error occurs when opening the socket
-     */
-    public static int getFreePort() throws InterruptedException, IOException {
-        int port = -1;
-
-        while (port <= 0) {
-            Thread.sleep(100);
-
-            ServerSocket serverSocket = null;
-            try {
-                serverSocket = new ServerSocket(0);
-                port = serverSocket.getLocalPort();
-            } finally {
-                serverSocket.close();
-            }
-        }
-
-        return port;
-    }
-
-    /**
-     * Returns the name of the local host.
-     *
-     * @return The host name
-     * @throws UnknownHostException if IP address of a host could not be determined
-     */
-    public static String getHostname() throws UnknownHostException {
-        InetAddress inetAddress = InetAddress.getLocalHost();
-        String hostName = inetAddress.getHostName();
-
-        assertTrue((hostName != null && !hostName.isEmpty()),
-                "Cannot get hostname");
-
-        return hostName;
-    }
-
-    /**
-     * Uses "jcmd -l" to search for a jvm pid. This function will wait
-     * forever (until jtreg timeout) for the pid to be found.
-     * @param key Regular expression to search for
-     * @return The found pid.
-     */
-    public static int waitForJvmPid(String key) throws Throwable {
-        final long iterationSleepMillis = 250;
-        System.out.println("waitForJvmPid: Waiting for key '" + key + "'");
-        System.out.flush();
-        while (true) {
-            int pid = tryFindJvmPid(key);
-            if (pid >= 0) {
-                return pid;
-            }
-            Thread.sleep(iterationSleepMillis);
-        }
-    }
-
-    /**
-     * Searches for a jvm pid in the output from "jcmd -l".
-     *
-     * Example output from jcmd is:
-     * 12498 sun.tools.jcmd.JCmd -l
-     * 12254 /tmp/jdk8/tl/jdk/JTwork/classes/com/sun/tools/attach/Application.jar
-     *
-     * @param key A regular expression to search for.
-     * @return The found pid, or -1 if Enot found.
-     * @throws Exception If multiple matching jvms are found.
-     */
-    public static int tryFindJvmPid(String key) throws Throwable {
-        OutputAnalyzer output = null;
-        try {
-            JDKToolLauncher jcmdLauncher = JDKToolLauncher.create("jcmd");
-            jcmdLauncher.addToolArg("-l");
-            output = ProcessTools.executeProcess(jcmdLauncher.getCommand());
-            output.shouldHaveExitValue(0);
-
-            // Search for a line starting with numbers (pid), follwed by the key.
-            Pattern pattern = Pattern.compile("([0-9]+)\\s.*(" + key + ").*\\r?\\n");
-            Matcher matcher = pattern.matcher(output.getStdout());
-
-            int pid = -1;
-            if (matcher.find()) {
-                pid = Integer.parseInt(matcher.group(1));
-                System.out.println("findJvmPid.pid: " + pid);
-                if (matcher.find()) {
-                    throw new Exception("Found multiple JVM pids for key: " + key);
-                }
-            }
-            return pid;
-        } catch (Throwable t) {
-            System.out.println(String.format("Utils.findJvmPid(%s) failed: %s", key, t));
-            throw t;
-        }
-    }
-
-    /**
-     * Return the contents of the named file as a single String,
-     * or null if not found.
-     * @param filename name of the file to read
-     * @return String contents of file, or null if file not found.
-     * @throws  IOException
-     *          if an I/O error occurs reading from the file or a malformed or
-     *          unmappable byte sequence is read
-     */
-    public static String fileAsString(String filename) throws IOException {
-        Path filePath = Paths.get(filename);
-        return Files.exists(filePath)
-            ? Files.lines(filePath).collect(Collectors.joining(NEW_LINE))
-            : null;
-    }
-
-    /**
-     * @return Unsafe instance.
-     */
-    public static synchronized Unsafe getUnsafe() {
-        if (unsafe == null) {
-            try {
-                Field f = Unsafe.class.getDeclaredField("theUnsafe");
-                f.setAccessible(true);
-                unsafe = (Unsafe) f.get(null);
-            } catch (NoSuchFieldException | IllegalAccessException e) {
-                throw new RuntimeException("Unable to get Unsafe instance.", e);
-            }
-        }
-        return unsafe;
-    }
-    private static final char[] hexArray = new char[]{'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F'};
-
-    /**
-     * Returns hex view of byte array
-     *
-     * @param bytes byte array to process
-     * @return Space separated hexadecimal string representation of bytes
-     */
-
-    public static String toHexString(byte[] bytes) {
-        char[] hexView = new char[bytes.length * 3];
-        int i = 0;
-        for (byte b : bytes) {
-            hexView[i++] = hexArray[(b >> 4) & 0x0F];
-            hexView[i++] = hexArray[b & 0x0F];
-            hexView[i++] = ' ';
-        }
-        return new String(hexView);
-    }
-
-    /**
-     * Returns {@link java.util.Random} generator initialized with particular seed.
-     * The seed could be provided via system property {@link Utils#SEED_PROPERTY_NAME}
-     * In case no seed is provided, the method uses a random number.
-     * The used seed printed to stdout.
-     * @return {@link java.util.Random} generator with particular seed.
-     */
-    public static Random getRandomInstance() {
-        if (RANDOM_GENERATOR == null) {
-            synchronized (Utils.class) {
-                if (RANDOM_GENERATOR == null) {
-                    RANDOM_GENERATOR = new Random(SEED);
-                    System.out.printf("For random generator using seed: %d%n", SEED);
-                    System.out.printf("To re-run test with same seed value please add \"-D%s=%d\" to command line.%n", SEED_PROPERTY_NAME, SEED);
-                }
-            }
-        }
-        return RANDOM_GENERATOR;
-    }
-
-    /**
-     * Wait for condition to be true
-     *
-     * @param condition, a condition to wait for
-     */
-    public static final void waitForCondition(BooleanSupplier condition) {
-        waitForCondition(condition, -1L, 100L);
-    }
-
-    /**
-     * Wait until timeout for condition to be true
-     *
-     * @param condition, a condition to wait for
-     * @param timeout a time in milliseconds to wait for condition to be true
-     * specifying -1 will wait forever
-     * @return condition value, to determine if wait was successfull
-     */
-    public static final boolean waitForCondition(BooleanSupplier condition,
-            long timeout) {
-        return waitForCondition(condition, timeout, 100L);
-    }
-
-    /**
-     * Wait until timeout for condition to be true for specified time
-     *
-     * @param condition, a condition to wait for
-     * @param timeout a time in milliseconds to wait for condition to be true,
-     * specifying -1 will wait forever
-     * @param sleepTime a time to sleep value in milliseconds
-     * @return condition value, to determine if wait was successfull
-     */
-    public static final boolean waitForCondition(BooleanSupplier condition,
-            long timeout, long sleepTime) {
-        long startTime = System.currentTimeMillis();
-        while (!(condition.getAsBoolean() || (timeout != -1L
-                && ((System.currentTimeMillis() - startTime) > timeout)))) {
-            try {
-                Thread.sleep(sleepTime);
-            } catch (InterruptedException e) {
-                Thread.currentThread().interrupt();
-                throw new Error(e);
-            }
-        }
-        return condition.getAsBoolean();
-    }
-
-    /**
-     * Adjusts the provided timeout value for the TIMEOUT_FACTOR
-     * @param tOut the timeout value to be adjusted
-     * @return The timeout value adjusted for the value of "test.timeout.factor"
-     *         system property
-     */
-    public static long adjustTimeout(long tOut) {
-        return Math.round(tOut * Utils.TIMEOUT_FACTOR);
-    }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/cli/CPUSpecificCommandLineOptionTest.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,65 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package com.oracle.java.testlibrary.cli;
-
-import com.oracle.java.testlibrary.cli.predicate.CPUSpecificPredicate;
-
-/**
- * Base class for command line options tests that
- * requires specific CPU arch or specific CPU features.
- */
-public abstract class CPUSpecificCommandLineOptionTest
-        extends CommandLineOptionTest {
-    /**
-     * Creates new CPU specific test instance that does not
-     * require any CPU features.
-     *
-     * @param cpuArchPattern Regular expression that should
-     *                       match os.arch.
-     */
-    public CPUSpecificCommandLineOptionTest(String cpuArchPattern) {
-        this(cpuArchPattern, null, null);
-    }
-
-    /**
-     * Creates new CPU specific test instance that does not
-     * require from CPU support of {@code supportedCPUFeatures} features
-     * and no support of {@code unsupportedCPUFeatures}.
-     *
-     * @param cpuArchPattern Regular expression that should
-     *                       match os.arch.
-     * @param supportedCPUFeatures Array with names of features that
-     *                             should be supported by CPU. If {@code null},
-     *                             then no features have to be supported.
-     * @param unsupportedCPUFeatures Array with names of features that
-     *                               should not be supported by CPU.
-     *                               If {@code null}, then CPU may support any
-     *                               features.
-     */
-    public CPUSpecificCommandLineOptionTest(String cpuArchPattern,
-            String supportedCPUFeatures[], String unsupportedCPUFeatures[]) {
-        super(new CPUSpecificPredicate(cpuArchPattern, supportedCPUFeatures,
-                unsupportedCPUFeatures));
-    }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/cli/CommandLineOptionTest.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,396 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package com.oracle.java.testlibrary.cli;
-
-import java.util.List;
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.function.BooleanSupplier;
-
-import com.oracle.java.testlibrary.*;
-
-/**
- * Base class for command line option tests.
- */
-public abstract class CommandLineOptionTest {
-    public static final String UNLOCK_DIAGNOSTIC_VM_OPTIONS
-            = "-XX:+UnlockDiagnosticVMOptions";
-    public static final String UNLOCK_EXPERIMENTAL_VM_OPTIONS
-            = "-XX:+UnlockExperimentalVMOptions";
-    protected static final String UNRECOGNIZED_OPTION_ERROR_FORMAT
-            = "Unrecognized VM option '[+-]?%s(=.*)?'";
-    protected static final String EXPERIMENTAL_OPTION_ERROR_FORMAT
-            = "VM option '%s' is experimental and must be enabled via "
-            + "-XX:\\+UnlockExperimentalVMOptions.";
-    protected static final String DIAGNOSTIC_OPTION_ERROR_FORMAT
-            = " VM option '%s' is diagnostic and must be enabled via "
-            + "-XX:\\+UnlockDiagnosticVMOptions.";
-    private static final String PRINT_FLAGS_FINAL_FORMAT = "%s\\s*:?=\\s*%s";
-
-    /**
-     * Verifies that JVM startup behavior matches our expectations.
-     *
-     * @param option an option that should be passed to JVM
-     * @param expectedMessages an array of patterns that should occur
-     *                          in JVM output. If {@code null} then
-     *                          JVM output could be empty.
-     * @param unexpectedMessages an array of patterns that should not
-     *                           occur in JVM output. If {@code null} then
-     *                           JVM output could be empty.
-     * @param exitErrorMessage message that will be shown if exit code is not
-     *                           as expected.
-     * @param wrongWarningMessage message that will be shown if warning
-     *                           messages are not as expected.
-     * @param exitCode expected exit code.
-     * @throws Throwable if verification fails or some other issues occur.
-     */
-    public static void verifyJVMStartup(String option,
-            String expectedMessages[], String unexpectedMessages[],
-            String exitErrorMessage, String wrongWarningMessage,
-            ExitCode exitCode) throws Throwable {
-        CommandLineOptionTest.verifyJVMStartup(expectedMessages,
-                unexpectedMessages, exitErrorMessage,
-                wrongWarningMessage, exitCode, false, option);
-    }
-
-    /**
-     * Verifies that JVM startup behavior matches our expectations.
-     *
-     * @param expectedMessages an array of patterns that should occur
-     *                         in JVM output. If {@code null} then
-     *                         JVM output could be empty.
-     * @param unexpectedMessages an array of patterns that should not
-     *                           occur in JVM output. If {@code null} then
-     *                           JVM output could be empty.
-     * @param exitErrorMessage message that will be shown if exit code is not
-     *                           as expected.
-     * @param wrongWarningMessage message that will be shown if warning
-     *                           messages are not as expected.
-     * @param exitCode expected exit code.
-     * @param addTestVMOptions if {@code true} then test VM options will be
-     *                         passed to VM.
-     * @param options options that should be passed to VM in addition to mode
-     *                flag.
-     * @throws Throwable if verification fails or some other issues occur.
-     */
-    public static void verifyJVMStartup(String expectedMessages[],
-            String unexpectedMessages[], String exitErrorMessage,
-            String wrongWarningMessage, ExitCode exitCode,
-            boolean addTestVMOptions, String... options)
-                    throws Throwable {
-        List<String> finalOptions = new ArrayList<>();
-        if (addTestVMOptions) {
-            Collections.addAll(finalOptions, Utils.getTestJavaOpts());
-        }
-        Collections.addAll(finalOptions, options);
-        finalOptions.add("-version");
-
-        ProcessBuilder processBuilder
-                = ProcessTools.createJavaProcessBuilder(finalOptions.toArray(
-                new String[finalOptions.size()]));
-        OutputAnalyzer outputAnalyzer
-                = new OutputAnalyzer(processBuilder.start());
-
-        try {
-                outputAnalyzer.shouldHaveExitValue(exitCode.value);
-        } catch (RuntimeException e) {
-            String errorMessage = String.format(
-                    "JVM process should have exit value '%d'.%n%s",
-                    exitCode.value, exitErrorMessage);
-            throw new AssertionError(errorMessage, e);
-        }
-
-
-        if (expectedMessages != null) {
-            for (String expectedMessage : expectedMessages) {
-                try {
-                    outputAnalyzer.shouldMatch(expectedMessage);
-                } catch (RuntimeException e) {
-                    String errorMessage = String.format(
-                            "Expected message not found: '%s'.%n%s",
-                            expectedMessage, wrongWarningMessage);
-                    throw new AssertionError(errorMessage, e);
-                }
-            }
-        }
-
-        if (unexpectedMessages != null) {
-            for (String unexpectedMessage : unexpectedMessages) {
-                try {
-                    outputAnalyzer.shouldNotMatch(unexpectedMessage);
-                } catch (RuntimeException e) {
-                    String errorMessage = String.format(
-                            "Unexpected message found: '%s'.%n%s",
-                            unexpectedMessage, wrongWarningMessage);
-                    throw new AssertionError(errorMessage, e);
-                }
-            }
-        }
-    }
-
-    /**
-     * Verifies that JVM startup behavior matches our expectations when type
-     * of newly started VM is the same as the type of current.
-     *
-     * @param expectedMessages an array of patterns that should occur
-     *                         in JVM output. If {@code null} then
-     *                         JVM output could be empty.
-     * @param unexpectedMessages an array of patterns that should not
-     *                           occur in JVM output. If {@code null} then
-     *                           JVM output could be empty.
-     * @param exitErrorMessage Message that will be shown if exit value is not
-     *                           as expected.
-     * @param wrongWarningMessage message that will be shown if warning
-     *                           messages are not as expected.
-     * @param exitCode expected exit code.
-     * @param options options that should be passed to VM in addition to mode
-     *                flag.
-     * @throws Throwable if verification fails or some other issues occur.
-     */
-    public static void verifySameJVMStartup(String expectedMessages[],
-            String unexpectedMessages[], String exitErrorMessage,
-            String wrongWarningMessage, ExitCode exitCode, String... options)
-            throws Throwable {
-        List<String> finalOptions = new ArrayList<>();
-        finalOptions.add(CommandLineOptionTest.getVMTypeOption());
-        Collections.addAll(finalOptions, options);
-
-        CommandLineOptionTest.verifyJVMStartup(expectedMessages,
-                unexpectedMessages, exitErrorMessage,
-                wrongWarningMessage, exitCode, false,
-                finalOptions.toArray(new String[finalOptions.size()]));
-    }
-
-    /**
-     * Verifies that value of specified JVM option is the same as
-     * expected value.
-     * This method filter out option with {@code optionName}
-     * name from test java options.
-     *
-     * @param optionName a name of tested option.
-     * @param expectedValue expected value of tested option.
-     * @param optionErrorString message will be shown if option value is not as
-     *                         expected.
-     * @param additionalVMOpts additional options that should be
-     *                         passed to JVM.
-     * @throws Throwable if verification fails or some other issues occur.
-     */
-    public static void verifyOptionValue(String optionName,
-            String expectedValue, String optionErrorString,
-            String... additionalVMOpts) throws Throwable {
-        verifyOptionValue(optionName, expectedValue,  optionErrorString,
-                true, additionalVMOpts);
-    }
-
-    /**
-     * Verifies that value of specified JVM option is the same as
-     * expected value.
-     * This method filter out option with {@code optionName}
-     * name from test java options.
-     *
-     * @param optionName a name of tested option.
-     * @param expectedValue expected value of tested option.
-     * @param addTestVmOptions if {@code true}, then test VM options
-     *                         will be used.
-     * @param optionErrorString message will be shown if option value is not as
-     *                         expected.
-     * @param additionalVMOpts additional options that should be
-     *                         passed to JVM.
-     * @throws Throwable if verification fails or some other issues
-     *                          occur.
-     */
-    public static void verifyOptionValue(String optionName,
-            String expectedValue, String optionErrorString,
-            boolean addTestVmOptions, String... additionalVMOpts)
-                    throws Throwable {
-        List<String> vmOpts = new ArrayList<>();
-
-        if (addTestVmOptions) {
-            Collections.addAll(vmOpts,
-                               Utils.getFilteredTestJavaOpts(optionName));
-        }
-        Collections.addAll(vmOpts, additionalVMOpts);
-        Collections.addAll(vmOpts, "-XX:+PrintFlagsFinal", "-version");
-
-        ProcessBuilder processBuilder = ProcessTools.createJavaProcessBuilder(
-                vmOpts.toArray(new String[vmOpts.size()]));
-
-        OutputAnalyzer outputAnalyzer
-                = new OutputAnalyzer(processBuilder.start());
-
-        try {
-            outputAnalyzer.shouldHaveExitValue(0);
-        } catch (RuntimeException e) {
-            String errorMessage = String.format(
-                    "JVM should start with option '%s' without errors.",
-                    optionName);
-            throw new AssertionError(errorMessage, e);
-        }
-        try {
-        outputAnalyzer.shouldMatch(String.format(
-                CommandLineOptionTest.PRINT_FLAGS_FINAL_FORMAT,
-                optionName, expectedValue));
-        } catch (RuntimeException e) {
-            String errorMessage =  String.format(
-                    "Option '%s' is expected to have '%s' value%n%s",
-                    optionName, expectedValue,
-                    optionErrorString);
-            throw new AssertionError(errorMessage, e);
-        }
-    }
-
-    /**
-     * Verifies that value of specified JVM when type of newly started VM
-     * is the same as the type of current.
-     * This method filter out option with {@code optionName}
-     * name from test java options.
-     * Only mode flag will be passed to VM in addition to
-     * {@code additionalVMOpts}
-     *
-     * @param optionName name of tested option.
-     * @param expectedValue expected value of tested option.
-     * @param optionErrorString message to show if option has another value
-     * @param additionalVMOpts additional options that should be
-     *                         passed to JVM.
-     * @throws Throwable if verification fails or some other issues occur.
-     */
-    public static void verifyOptionValueForSameVM(String optionName,
-            String expectedValue, String optionErrorString,
-            String... additionalVMOpts) throws Throwable {
-        List<String> finalOptions = new ArrayList<>();
-        finalOptions.add(CommandLineOptionTest.getVMTypeOption());
-        Collections.addAll(finalOptions, additionalVMOpts);
-
-        CommandLineOptionTest.verifyOptionValue(optionName, expectedValue,
-                optionErrorString, false,
-                finalOptions.toArray(new String[finalOptions.size()]));
-    }
-
-    /**
-     * Prepares boolean command line flag with name {@code name} according
-     * to it's {@code value}.
-     *
-     * @param name the name of option to be prepared
-     * @param value the value of option
-     * @return prepared command line flag
-     */
-    public static String prepareBooleanFlag(String name, boolean value) {
-        return String.format("-XX:%c%s", (value ? '+' : '-'), name);
-    }
-
-    /**
-     * Prepares numeric command line flag with name {@code name} by setting
-     * it's value to {@code value}.
-     *
-     * @param name the name of option to be prepared
-     * @param value the value of option
-     * @return prepared command line flag
-     */
-    public static String prepareNumericFlag(String name, Number value) {
-        return String.format("-XX:%s=%s", name, value.toString());
-    }
-
-    /**
-     * Returns message that should occur in VM output if option
-     * {@code optionName} if unrecognized.
-     *
-     * @param optionName the name of option for which message should be returned
-     * @return message saying that option {@code optionName} is unrecognized
-     */
-    public static String getUnrecognizedOptionErrorMessage(String optionName) {
-        return String.format(
-                CommandLineOptionTest.UNRECOGNIZED_OPTION_ERROR_FORMAT,
-                optionName);
-    }
-
-    /**
-     * Returns message that should occur in VM output if option
-     * {@code optionName} is experimental and
-     * -XX:+UnlockExperimentalVMOptions was not passed to VM.
-     *
-     * @param optionName the name of option for which message should be returned
-     * @return message saying that option {@code optionName} is experimental
-     */
-    public static String getExperimentalOptionErrorMessage(String optionName) {
-        return String.format(
-                CommandLineOptionTest.EXPERIMENTAL_OPTION_ERROR_FORMAT,
-                optionName);
-    }
-
-    /**
-     * Returns message that should occur in VM output if option
-     * {@code optionName} is diagnostic and -XX:+UnlockDiagnosticVMOptions
-     * was not passed to VM.
-     *
-     * @param optionName the name of option for which message should be returned
-     * @return message saying that option {@code optionName} is diganostic
-     */
-    public static String getDiagnosticOptionErrorMessage(String optionName) {
-        return String.format(
-                CommandLineOptionTest.DIAGNOSTIC_OPTION_ERROR_FORMAT,
-                optionName);
-    }
-
-    /**
-     * @return option required to start a new VM with the same type as current.
-     * @throws RuntimeException when VM type is unknown.
-     */
-    private static String getVMTypeOption() {
-        if (Platform.isServer()) {
-            return "-server";
-        } else if (Platform.isClient()) {
-            return "-client";
-        } else if (Platform.isMinimal()) {
-            return "-minimal";
-        } else if (Platform.isGraal()) {
-            return "-graal";
-        }
-        throw new RuntimeException("Unknown VM mode.");
-    }
-
-    private final BooleanSupplier predicate;
-
-    /**
-     * Constructs new CommandLineOptionTest that will be executed only if
-     * predicate {@code predicate} return {@code true}.
-     * @param predicate a predicate responsible for test's preconditions check.
-     */
-    public CommandLineOptionTest(BooleanSupplier predicate) {
-        this.predicate = predicate;
-    }
-
-    /**
-     * Runs command line option test.
-     */
-    public final void test() throws Throwable {
-        if (predicate.getAsBoolean()) {
-            runTestCases();
-        }
-    }
-
-    /**
-     * @throws Throwable if some issue happened during test cases execution.
-     */
-    protected abstract void runTestCases() throws Throwable;
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/cli/predicate/AndPredicate.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,41 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package com.oracle.java.testlibrary.cli.predicate;
-
-import java.util.function.BooleanSupplier;
-
-public class AndPredicate implements BooleanSupplier {
-    private final BooleanSupplier a;
-    private final BooleanSupplier b;
-
-    public AndPredicate(BooleanSupplier a, BooleanSupplier b) {
-        this.a = a;
-        this.b = b;
-    }
-
-    @Override
-    public boolean getAsBoolean() {
-        return a.getAsBoolean() && b.getAsBoolean();
-    }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/cli/predicate/CPUSpecificPredicate.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,71 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package com.oracle.java.testlibrary.cli.predicate;
-
-import com.oracle.java.testlibrary.Platform;
-import sun.hotspot.cpuinfo.CPUInfo;
-
-import java.util.function.BooleanSupplier;
-
-public class CPUSpecificPredicate implements BooleanSupplier {
-    private final String cpuArchPattern;
-    private final String supportedCPUFeatures[];
-    private final String unsupportedCPUFeatures[];
-
-    public CPUSpecificPredicate(String cpuArchPattern,
-            String supportedCPUFeatures[],
-            String unsupportedCPUFeatures[]) {
-        this.cpuArchPattern = cpuArchPattern;
-        this.supportedCPUFeatures = supportedCPUFeatures;
-        this.unsupportedCPUFeatures = unsupportedCPUFeatures;
-    }
-
-    @Override
-    public boolean getAsBoolean() {
-        if (!Platform.getOsArch().matches(cpuArchPattern)) {
-            System.out.println("CPU arch does not match " + cpuArchPattern);
-            return false;
-        }
-
-        if (supportedCPUFeatures != null) {
-            for (String feature : supportedCPUFeatures) {
-                if (!CPUInfo.hasFeature(feature)) {
-                    System.out.println("CPU does not support " + feature
-                            + " feature");
-                    return false;
-                }
-            }
-        }
-
-        if (unsupportedCPUFeatures != null) {
-            for (String feature : unsupportedCPUFeatures) {
-                if (CPUInfo.hasFeature(feature)) {
-                    System.out.println("CPU support " + feature + " feature");
-                    return false;
-                }
-            }
-        }
-        return true;
-    }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/cli/predicate/NotPredicate.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,40 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- *
- */
-
-package com.oracle.java.testlibrary.cli.predicate;
-
-import java.util.function.BooleanSupplier;
-
-public class NotPredicate implements BooleanSupplier {
-    private final BooleanSupplier s;
-
-    public NotPredicate(BooleanSupplier s) {
-        this.s = s;
-    }
-
-    @Override
-    public boolean getAsBoolean() {
-        return !s.getAsBoolean();
-    }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/cli/predicate/OrPredicate.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,42 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- *
- */
-
-package com.oracle.java.testlibrary.cli.predicate;
-
-import java.util.function.BooleanSupplier;
-
-public class OrPredicate implements BooleanSupplier {
-    private final BooleanSupplier a;
-    private final BooleanSupplier b;
-
-    public OrPredicate(BooleanSupplier a, BooleanSupplier b) {
-        this.a = a;
-        this.b = b;
-    }
-
-    @Override
-    public boolean getAsBoolean() {
-        return a.getAsBoolean() || b.getAsBoolean();
-    }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/dcmd/CommandExecutor.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,75 +0,0 @@
-/*
- * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package com.oracle.java.testlibrary.dcmd;
-
-import com.oracle.java.testlibrary.OutputAnalyzer;
-
-/**
- * Abstract base class for Diagnostic Command executors
- */
-public abstract class CommandExecutor {
-
-    /**
-     * Execute a diagnostic command
-     *
-     * @param cmd The diagnostic command to execute
-     * @return an {@link jdk.testlibrary.OutputAnalyzer} encapsulating the output of the command
-     * @throws CommandExecutorException if there is an exception on the "calling side" while trying to execute the
-     *          Diagnostic Command. Exceptions thrown on the remote side are available as textual representations in
-     *          stderr, regardless of the specific executor used.
-     */
-    public final OutputAnalyzer execute(String cmd) throws CommandExecutorException {
-        return execute(cmd, false);
-    }
-
-    /**
-     * Execute a diagnostic command
-     *
-     * @param cmd The diagnostic command to execute
-     * @param silent Do not print the command output
-     * @return an {@link jdk.testlibrary.OutputAnalyzer} encapsulating the output of the command
-     * @throws CommandExecutorException if there is an exception on the "calling side" while trying to execute the
-     *          Diagnostic Command. Exceptions thrown on the remote side are available as textual representations in
-     *          stderr, regardless of the specific executor used.
-     */
-    public final OutputAnalyzer execute(String cmd, boolean silent) throws CommandExecutorException {
-        if (!silent) {
-            System.out.printf("Running DCMD '%s' through '%s'%n", cmd, this.getClass().getSimpleName());
-        }
-
-        OutputAnalyzer oa = executeImpl(cmd);
-
-        if (!silent) {
-            System.out.println("---------------- stdout ----------------");
-            System.out.println(oa.getStdout());
-            System.out.println("---------------- stderr ----------------");
-            System.out.println(oa.getStderr());
-            System.out.println("----------------------------------------");
-            System.out.println();
-        }
-        return oa;
-    }
-
-    protected abstract OutputAnalyzer executeImpl(String cmd) throws CommandExecutorException;
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/dcmd/CommandExecutorException.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,36 +0,0 @@
-/*
- * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package com.oracle.java.testlibrary.dcmd;
-
-/**
- * CommandExecutorException encapsulates exceptions thrown (on the "calling side") from the execution of Diagnostic
- * Commands
- */
-public class CommandExecutorException extends RuntimeException {
-    private static final long serialVersionUID = -7039597746579144280L;
-
-    public CommandExecutorException(String message, Throwable e) {
-        super(message, e);
-    }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/dcmd/FileJcmdExecutor.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,81 +0,0 @@
-/*
- * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package com.oracle.java.testlibrary.dcmd;
-
-import java.io.File;
-import java.io.IOException;
-import java.io.PrintWriter;
-import java.util.Arrays;
-import java.util.List;
-
-/**
- * Executes Diagnostic Commands on the target VM (specified by pid) using the jcmd tool and its ability to read
- *          Diagnostic Commands from a file.
- */
-public class FileJcmdExecutor extends PidJcmdExecutor {
-
-    /**
-     * Instantiates a new FileJcmdExecutor targeting the current VM
-     */
-    public FileJcmdExecutor() {
-        super();
-    }
-
-    /**
-     * Instantiates a new FileJcmdExecutor targeting the VM indicated by the given pid
-     *
-     * @param target Pid of the target VM
-     */
-    public FileJcmdExecutor(String target) {
-        super(target);
-    }
-
-    protected List<String> createCommandLine(String cmd) throws CommandExecutorException {
-        File cmdFile = createTempFile();
-        writeCommandToTemporaryFile(cmd, cmdFile);
-
-        return Arrays.asList(jcmdBinary, Integer.toString(pid),
-                "-f", cmdFile.getAbsolutePath());
-    }
-
-    private void writeCommandToTemporaryFile(String cmd, File cmdFile) {
-        try (PrintWriter pw = new PrintWriter(cmdFile)) {
-            pw.println(cmd);
-        } catch (IOException e) {
-            String message = "Could not write to file: " + cmdFile.getAbsolutePath();
-            throw new CommandExecutorException(message, e);
-        }
-    }
-
-    private File createTempFile() {
-        try {
-            File cmdFile = File.createTempFile("input", "jcmd");
-            cmdFile.deleteOnExit();
-            return cmdFile;
-        } catch (IOException e) {
-            throw new CommandExecutorException("Could not create temporary file", e);
-        }
-    }
-
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/dcmd/JMXExecutor.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,187 +0,0 @@
-/*
- * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package com.oracle.java.testlibrary.dcmd;
-
-import com.oracle.java.testlibrary.OutputAnalyzer;
-
-import javax.management.*;
-import javax.management.remote.JMXConnector;
-import javax.management.remote.JMXConnectorFactory;
-import javax.management.remote.JMXServiceURL;
-
-import java.io.IOException;
-import java.io.PrintWriter;
-import java.io.StringWriter;
-
-import java.lang.management.ManagementFactory;
-
-import java.util.HashMap;
-
-/**
- * Executes Diagnostic Commands on the target VM (specified by a host/port combination or a full JMX Service URL) using
- * the JMX interface. If the target is not the current VM, the JMX Remote interface must be enabled beforehand.
- */
-public class JMXExecutor extends CommandExecutor {
-
-    private final MBeanServerConnection mbs;
-
-    /**
-     * Instantiates a new JMXExecutor targeting the current VM
-     */
-    public JMXExecutor() {
-        super();
-        mbs = ManagementFactory.getPlatformMBeanServer();
-    }
-
-    /**
-     * Instantiates a new JMXExecutor targeting the VM indicated by the given host/port combination or a full JMX
-     * Service URL
-     *
-     * @param target a host/port combination on the format "host:port" or a full JMX Service URL of the target VM
-     */
-    public JMXExecutor(String target) {
-        String urlStr;
-
-        if (target.matches("^\\w[\\w\\-]*(\\.[\\w\\-]+)*:\\d+$")) {
-            /* Matches "hostname:port" */
-            urlStr = String.format("service:jmx:rmi:///jndi/rmi://%s/jmxrmi", target);
-        } else if (target.startsWith("service:")) {
-            urlStr = target;
-        } else {
-            throw new IllegalArgumentException("Could not recognize target string: " + target);
-        }
-
-        try {
-            JMXServiceURL url = new JMXServiceURL(urlStr);
-            JMXConnector c = JMXConnectorFactory.connect(url, new HashMap<>());
-            mbs = c.getMBeanServerConnection();
-        } catch (IOException e) {
-            throw new CommandExecutorException("Could not initiate connection to target: " + target, e);
-        }
-    }
-
-    protected OutputAnalyzer executeImpl(String cmd) throws CommandExecutorException {
-        String stdout = "";
-        String stderr = "";
-
-        String[] cmdParts = cmd.split(" ", 2);
-        String operation = commandToMethodName(cmdParts[0]);
-        Object[] dcmdArgs = produceArguments(cmdParts);
-        String[] signature = {String[].class.getName()};
-
-        ObjectName beanName = getMBeanName();
-
-        try {
-            stdout = (String) mbs.invoke(beanName, operation, dcmdArgs, signature);
-        }
-
-        /* Failures on the "local" side, the one invoking the command. */
-        catch (ReflectionException e) {
-            Throwable cause = e.getCause();
-            if (cause instanceof NoSuchMethodException) {
-                /* We want JMXExecutor to match the behavior of the other CommandExecutors */
-                String message = "Unknown diagnostic command: " + operation;
-                stderr = exceptionTraceAsString(new IllegalArgumentException(message, e));
-            } else {
-                rethrowExecutorException(operation, dcmdArgs, e);
-            }
-        }
-
-        /* Failures on the "local" side, the one invoking the command. */
-        catch (InstanceNotFoundException | IOException e) {
-            rethrowExecutorException(operation, dcmdArgs, e);
-        }
-
-        /* Failures on the remote side, the one executing the invoked command. */
-        catch (MBeanException e) {
-            stdout = exceptionTraceAsString(e);
-        }
-
-        return new OutputAnalyzer(stdout, stderr);
-    }
-
-    private void rethrowExecutorException(String operation, Object[] dcmdArgs,
-                                          Exception e) throws CommandExecutorException {
-        String message = String.format("Could not invoke: %s %s", operation,
-                String.join(" ", (String[]) dcmdArgs[0]));
-        throw new CommandExecutorException(message, e);
-    }
-
-    private ObjectName getMBeanName() throws CommandExecutorException {
-        String MBeanName = "com.sun.management:type=DiagnosticCommand";
-
-        try {
-            return new ObjectName(MBeanName);
-        } catch (MalformedObjectNameException e) {
-            String message = "MBean not found: " + MBeanName;
-            throw new CommandExecutorException(message, e);
-        }
-    }
-
-    private Object[] produceArguments(String[] cmdParts) {
-        Object[] dcmdArgs = {new String[0]}; /* Default: No arguments */
-
-        if (cmdParts.length == 2) {
-            dcmdArgs[0] = cmdParts[1].split(" ");
-        }
-        return dcmdArgs;
-    }
-
-    /**
-     * Convert from diagnostic command to MBean method name
-     *
-     * Examples:
-     * help            --> help
-     * VM.version      --> vmVersion
-     * VM.command_line --> vmCommandLine
-     */
-    private static String commandToMethodName(String cmd) {
-        String operation = "";
-        boolean up = false; /* First letter is to be lower case */
-
-        /*
-         * If a '.' or '_' is encountered it is not copied,
-         * instead the next character will be converted to upper case
-         */
-        for (char c : cmd.toCharArray()) {
-            if (('.' == c) || ('_' == c)) {
-                up = true;
-            } else if (up) {
-                operation = operation.concat(Character.toString(c).toUpperCase());
-                up = false;
-            } else {
-                operation = operation.concat(Character.toString(c).toLowerCase());
-            }
-        }
-
-        return operation;
-    }
-
-    private static String exceptionTraceAsString(Throwable cause) {
-        StringWriter sw = new StringWriter();
-        cause.printStackTrace(new PrintWriter(sw));
-        return sw.toString();
-    }
-
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/dcmd/JcmdExecutor.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,58 +0,0 @@
-/*
- * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package com.oracle.java.testlibrary.dcmd;
-
-import com.oracle.java.testlibrary.JDKToolFinder;
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
-
-import java.util.List;
-
-/**
- * Base class for Diagnostic Command Executors using the jcmd tool
- */
-public abstract class JcmdExecutor extends CommandExecutor {
-    protected String jcmdBinary;
-
-    protected abstract List<String> createCommandLine(String cmd) throws CommandExecutorException;
-
-    protected JcmdExecutor() {
-        jcmdBinary = JDKToolFinder.getJDKTool("jcmd");
-    }
-
-    protected OutputAnalyzer executeImpl(String cmd) throws CommandExecutorException {
-        List<String> commandLine = createCommandLine(cmd);
-
-        try {
-            System.out.printf("Executing command '%s'%n", commandLine);
-            OutputAnalyzer output = ProcessTools.executeProcess(new ProcessBuilder(commandLine));
-            System.out.printf("Command returned with exit code %d%n", output.getExitValue());
-
-            return output;
-        } catch (Exception e) {
-            String message = String.format("Caught exception while executing '%s'", commandLine);
-            throw new CommandExecutorException(message, e);
-        }
-    }
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/dcmd/MainClassJcmdExecutor.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,57 +0,0 @@
-/*
- * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package com.oracle.java.testlibrary.dcmd;
-
-import java.util.Arrays;
-import java.util.List;
-
-/**
- * Executes Diagnostic Commands on the target VM (specified by main class) using the jcmd tool
- */
-public class MainClassJcmdExecutor extends JcmdExecutor {
-    private final String mainClass;
-
-    /**
-     * Instantiates a new MainClassJcmdExecutor targeting the current VM
-     */
-    public MainClassJcmdExecutor() {
-        super();
-        mainClass = System.getProperty("sun.java.command").split(" ")[0];
-    }
-
-    /**
-     * Instantiates a new MainClassJcmdExecutor targeting the VM indicated by the given main class
-     *
-     * @param target Main class of the target VM
-     */
-    public MainClassJcmdExecutor(String target) {
-        super();
-        mainClass = target;
-    }
-
-    protected List<String> createCommandLine(String cmd) throws CommandExecutorException {
-        return Arrays.asList(jcmdBinary, mainClass, cmd);
-    }
-
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/dcmd/PidJcmdExecutor.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,63 +0,0 @@
-/*
- * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package com.oracle.java.testlibrary.dcmd;
-
-import com.oracle.java.testlibrary.ProcessTools;
-
-import java.util.Arrays;
-import java.util.List;
-
-/**
- * Executes Diagnostic Commands on the target VM (specified by pid) using the jcmd tool
- */
-public class PidJcmdExecutor extends JcmdExecutor {
-    protected final int pid;
-
-    /**
-     * Instantiates a new PidJcmdExecutor targeting the current VM
-     */
-    public PidJcmdExecutor() {
-        super();
-        try {
-            pid = ProcessTools.getProcessId();
-        } catch (Exception e) {
-            throw new CommandExecutorException("Could not determine own pid", e);
-        }
-    }
-
-    /**
-     * Instantiates a new PidJcmdExecutor targeting the VM indicated by the given pid
-     *
-     * @param target Pid of the target VM
-     */
-    public PidJcmdExecutor(String target) {
-        super();
-        pid = Integer.valueOf(target);
-    }
-
-    protected List<String> createCommandLine(String cmd) throws CommandExecutorException {
-        return Arrays.asList(jcmdBinary, Integer.toString(pid), cmd);
-    }
-
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/dtrace/DtraceResultsAnalyzer.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,29 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-package com.oracle.java.testlibrary.dtrace;
-
-import com.oracle.java.testlibrary.OutputAnalyzer;
-
-public interface DtraceResultsAnalyzer {
-    public void analyze(OutputAnalyzer oa, String logFilePath);
-}
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/dtrace/DtraceRunner.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,121 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-package com.oracle.java.testlibrary.dtrace;
-
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import java.io.File;
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.List;
-
-public class DtraceRunner {
-
-    private static final String DTRACE_DEFAULT_PATH = "/usr/sbin/dtrace";
-    private static final String DTRACE_PATH_PROPERTY
-            = "com.oracle.test.dtrace.path";
-    private static final String OUTPUT_FILE_DTRACE_OPTION = "o";
-    private static final String RUN_COMMAND_DTRACE_OPTION = "c";
-    private static final String RUN_SCRIPT_DTRACE_OPTION = "s";
-    private static final String ALLOW_ZERO_PROBE_DESCRIPTION_DTRACE_OPTION = "Z";
-    private static final String DTRACE_OPTION_PREFIX = "-";
-    public static final String PERMIT_DESTRUCTIVE_ACTIONS_DTRACE_OPTION = "w";
-    public static final String DTRACE_OUT_LOG = "dtrace.out";
-
-    private final String dtraceExecutable;
-
-    public DtraceRunner() {
-        dtraceExecutable = getDtracePath();
-    }
-
-    private List<String> getLaunchCmd(String java, String javaOpts,
-            String execClass, String testArgs, String dtraceScript,
-            String dtraceAddOpts) {
-        Asserts.assertTrue(!java.matches("\\s"), "Current dtrace implementation"
-                + " can't handle whitespaces in application path");
-        List<String> result = new ArrayList<>();
-        result.add(dtraceExecutable);
-        result.add(DTRACE_OPTION_PREFIX + System.getProperty("sun.arch.data.model"));
-        result.add(DTRACE_OPTION_PREFIX
-                + ALLOW_ZERO_PROBE_DESCRIPTION_DTRACE_OPTION
-                + ((dtraceAddOpts == null) ? "" : dtraceAddOpts)
-                + RUN_SCRIPT_DTRACE_OPTION); // run_script should be last one
-        result.add(dtraceScript);
-        result.add(DTRACE_OPTION_PREFIX + OUTPUT_FILE_DTRACE_OPTION);
-        result.add(DTRACE_OUT_LOG);
-        result.add(DTRACE_OPTION_PREFIX + RUN_COMMAND_DTRACE_OPTION);
-        result.add(java + " " + javaOpts + " " + execClass + " " + testArgs);
-        return result;
-    }
-
-    private void backupLogFile(File file) {
-        if (file.exists()) {
-            file.renameTo(new File(file.getPath() + ".bak"));
-        }
-    }
-
-    public void runDtrace(String java, String javaOpts, String execClass,
-            String testArgs, String dtraceScript, String dtraceAddOpts,
-            DtraceResultsAnalyzer analyzer) {
-        backupLogFile(new File(DTRACE_OUT_LOG));
-        ProcessBuilder pbuilder = new ProcessBuilder(
-                getLaunchCmd(java, javaOpts, execClass, testArgs,
-                        dtraceScript, dtraceAddOpts));
-        OutputAnalyzer oa;
-        try {
-            oa = new OutputAnalyzer(pbuilder.start());
-        } catch (IOException e) {
-            throw new Error("TESTBUG: Can't start process", e);
-        }
-        analyzer.analyze(oa, DTRACE_OUT_LOG);
-    }
-
-    public static boolean dtraceAvailable() {
-        String path = getDtracePath();
-        if (path == null) {
-            return false;
-        }
-        // now we'll launch dtrace to trace itself just to be sure it works
-        // and have all additional previleges set
-        ProcessBuilder pbuilder = new ProcessBuilder(path, path);
-        try {
-            OutputAnalyzer oa = new OutputAnalyzer(pbuilder.start());
-            if (oa.getExitValue() != 0) {
-                return false;
-            }
-        } catch (IOException e) {
-            throw new Error("Couldn't launch dtrace", e);
-        }
-        return true;
-    }
-
-    private static String getDtracePath() {
-        String propPath = System.getProperty(DTRACE_PATH_PROPERTY);
-        if (propPath != null && new File(propPath).exists()) {
-            return propPath;
-        } else if (new File(DTRACE_DEFAULT_PATH).exists()) {
-            return DTRACE_DEFAULT_PATH;
-        }
-        return null;
-    }
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/Asserts.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,451 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib;
+
+/**
+ * Asserts that can be used for verifying assumptions in tests.
+ *
+ * An assertion will throw a {@link RuntimeException} if the assertion isn't
+ * valid.  All the asserts can be imported into a test by using a static
+ * import:
+ *
+ * <pre>
+ * {@code
+ * import static jdk.test.lib.Asserts.*;
+ * }
+ *
+ * Always provide a message describing the assumption if the line number of the
+ * failing assertion isn't enough to understand why the assumption failed. For
+ * example, if the assertion is in a loop or in a method that is called
+ * multiple times, then the line number won't provide enough context to
+ * understand the failure.
+ * </pre>
+ */
+public class Asserts {
+
+    /**
+     * Shorthand for {@link #assertLessThan(T, T)}.
+     *
+     * @see #assertLessThan(T, T)
+     */
+    public static <T extends Comparable<T>> void assertLT(T lhs, T rhs) {
+        assertLessThan(lhs, rhs);
+    }
+
+    /**
+     * Shorthand for {@link #assertLessThan(T, T, String)}.
+     *
+     * @see #assertLessThan(T, T, String)
+     */
+    public static <T extends Comparable<T>> void assertLT(T lhs, T rhs, String msg) {
+        assertLessThan(lhs, rhs, msg);
+    }
+
+    /**
+     * Calls {@link #assertLessThan(T, T, String)} with a default message.
+     *
+     * @see #assertLessThan(T, T, String)
+     */
+    public static <T extends Comparable<T>> void assertLessThan(T lhs, T rhs) {
+        assertLessThan(lhs, rhs, null);
+    }
+
+    /**
+     * Asserts that {@code lhs} is less than {@code rhs}.
+     *
+     * @param lhs The left hand side of the comparison.
+     * @param rhs The right hand side of the comparison.
+     * @param msg A description of the assumption.
+     * @throws RuntimeException if the assertion isn't valid.
+     */
+    public static <T extends Comparable<T>>void assertLessThan(T lhs, T rhs, String msg) {
+        assertTrue(compare(lhs, rhs, msg) < 0, getMessage(lhs, rhs, "<", msg));
+    }
+
+    /**
+     * Shorthand for {@link #assertLessThanOrEqual(T, T)}.
+     *
+     * @see #assertLessThanOrEqual(T, T)
+     */
+    public static <T extends Comparable<T>> void assertLTE(T lhs, T rhs) {
+        assertLessThanOrEqual(lhs, rhs);
+    }
+
+    /**
+     * Shorthand for {@link #assertLessThanOrEqual(T, T, String)}.
+     *
+     * @see #assertLessThanOrEqual(T, T, String)
+     */
+    public static <T extends Comparable<T>> void assertLTE(T lhs, T rhs, String msg) {
+        assertLessThanOrEqual(lhs, rhs, msg);
+    }
+
+    /**
+     * Calls {@link #assertLessThanOrEqual(T, T, String)} with a default message.
+     *
+     * @see #assertLessThanOrEqual(T, T, String)
+     */
+    public static <T extends Comparable<T>> void assertLessThanOrEqual(T lhs, T rhs) {
+        assertLessThanOrEqual(lhs, rhs, null);
+    }
+
+    /**
+     * Asserts that {@code lhs} is less than or equal to {@code rhs}.
+     *
+     * @param lhs The left hand side of the comparison.
+     * @param rhs The right hand side of the comparison.
+     * @param msg A description of the assumption.
+     * @throws RuntimeException if the assertion isn't valid.
+     */
+    public static <T extends Comparable<T>> void assertLessThanOrEqual(T lhs, T rhs, String msg) {
+        assertTrue(compare(lhs, rhs, msg) <= 0, getMessage(lhs, rhs, "<=", msg));
+    }
+
+    /**
+     * Shorthand for {@link #assertEquals(T, T)}.
+     *
+     * @see #assertEquals(T, T)
+     */
+    public static void assertEQ(Object lhs, Object rhs) {
+        assertEquals(lhs, rhs);
+    }
+
+    /**
+     * Shorthand for {@link #assertEquals(T, T, String)}.
+     *
+     * @see #assertEquals(T, T, String)
+     */
+    public static void assertEQ(Object lhs, Object rhs, String msg) {
+        assertEquals(lhs, rhs, msg);
+    }
+
+    /**
+     * Calls {@link #assertEquals(T, T, String)} with a default message.
+     *
+     * @see #assertEquals(T, T, String)
+     */
+    public static void assertEquals(Object lhs, Object rhs) {
+        assertEquals(lhs, rhs, null);
+    }
+
+    /**
+     * Asserts that {@code lhs} is equal to {@code rhs}.
+     *
+     * @param lhs The left hand side of the comparison.
+     * @param rhs The right hand side of the comparison.
+     * @param msg A description of the assumption.
+     * @throws RuntimeException if the assertion isn't valid.
+     */
+    public static void assertEquals(Object lhs, Object rhs, String msg) {
+        if (lhs == null) {
+            if (rhs != null) {
+                error(msg);
+            }
+        } else {
+            assertTrue(lhs.equals(rhs), getMessage(lhs, rhs, "==", msg));
+        }
+    }
+
+    /**
+     * Shorthand for {@link #assertGreaterThanOrEqual(T, T)}.
+     *
+     * @see #assertGreaterThanOrEqual(T, T)
+     */
+    public static <T extends Comparable<T>> void assertGTE(T lhs, T rhs) {
+        assertGreaterThanOrEqual(lhs, rhs);
+    }
+
+    /**
+     * Shorthand for {@link #assertGreaterThanOrEqual(T, T, String)}.
+     *
+     * @see #assertGreaterThanOrEqual(T, T, String)
+     */
+    public static <T extends Comparable<T>> void assertGTE(T lhs, T rhs, String msg) {
+        assertGreaterThanOrEqual(lhs, rhs, msg);
+    }
+
+    /**
+     * Calls {@link #assertGreaterThanOrEqual(T, T, String)} with a default message.
+     *
+     * @see #assertGreaterThanOrEqual(T, T, String)
+     */
+    public static <T extends Comparable<T>> void assertGreaterThanOrEqual(T lhs, T rhs) {
+        assertGreaterThanOrEqual(lhs, rhs, null);
+    }
+
+    /**
+     * Asserts that {@code lhs} is greater than or equal to {@code rhs}.
+     *
+     * @param lhs The left hand side of the comparison.
+     * @param rhs The right hand side of the comparison.
+     * @param msg A description of the assumption.
+     * @throws RuntimeException if the assertion isn't valid.
+     */
+    public static <T extends Comparable<T>> void assertGreaterThanOrEqual(T lhs, T rhs, String msg) {
+        assertTrue(compare(lhs, rhs, msg) >= 0, getMessage(lhs, rhs, ">=", msg));
+    }
+
+    /**
+     * Shorthand for {@link #assertGreaterThan(T, T)}.
+     *
+     * @see #assertGreaterThan(T, T)
+     */
+    public static <T extends Comparable<T>> void assertGT(T lhs, T rhs) {
+        assertGreaterThan(lhs, rhs);
+    }
+
+    /**
+     * Shorthand for {@link #assertGreaterThan(T, T, String)}.
+     *
+     * @see #assertGreaterThan(T, T, String)
+     */
+    public static <T extends Comparable<T>> void assertGT(T lhs, T rhs, String msg) {
+        assertGreaterThan(lhs, rhs, msg);
+    }
+
+    /**
+     * Calls {@link #assertGreaterThan(T, T, String)} with a default message.
+     *
+     * @see #assertGreaterThan(T, T, String)
+     */
+    public static <T extends Comparable<T>> void assertGreaterThan(T lhs, T rhs) {
+        assertGreaterThan(lhs, rhs, null);
+    }
+
+    /**
+     * Asserts that {@code lhs} is greater than {@code rhs}.
+     *
+     * @param lhs The left hand side of the comparison.
+     * @param rhs The right hand side of the comparison.
+     * @param msg A description of the assumption.
+     * @throws RuntimeException if the assertion isn't valid.
+     */
+    public static <T extends Comparable<T>> void assertGreaterThan(T lhs, T rhs, String msg) {
+        assertTrue(compare(lhs, rhs, msg) > 0, getMessage(lhs, rhs, ">", msg));
+    }
+
+    /**
+     * Shorthand for {@link #assertNotEquals(T, T)}.
+     *
+     * @see #assertNotEquals(T, T)
+     */
+    public static void assertNE(Object lhs, Object rhs) {
+        assertNotEquals(lhs, rhs);
+    }
+
+    /**
+     * Shorthand for {@link #assertNotEquals(T, T, String)}.
+     *
+     * @see #assertNotEquals(T, T, String)
+     */
+    public static void assertNE(Object lhs, Object rhs, String msg) {
+        assertNotEquals(lhs, rhs, msg);
+    }
+
+    /**
+     * Calls {@link #assertNotEquals(T, T, String)} with a default message.
+     *
+     * @see #assertNotEquals(T, T, String)
+     */
+    public static void assertNotEquals(Object lhs, Object rhs) {
+        assertNotEquals(lhs, rhs, null);
+    }
+
+    /**
+     * Asserts that {@code lhs} is not equal to {@code rhs}.
+     *
+     * @param lhs The left hand side of the comparison.
+     * @param rhs The right hand side of the comparison.
+     * @param msg A description of the assumption.
+     * @throws RuntimeException if the assertion isn't valid.
+     */
+    public static void assertNotEquals(Object lhs, Object rhs, String msg) {
+        if (lhs == null) {
+            if (rhs == null) {
+                error(msg);
+            }
+        } else {
+            assertFalse(lhs.equals(rhs), getMessage(lhs, rhs,"!=", msg));
+        }
+    }
+
+    /**
+     * Calls {@link #assertNull(Object, String)} with a default message.
+     *
+     * @see #assertNull(Object, String)
+     */
+    public static void assertNull(Object o) {
+        assertNull(o, "Expected " + format(o) + " to be null");
+    }
+
+    /**
+     * Asserts that {@code o} is null.
+     *
+     * @param o The reference assumed to be null.
+     * @param msg A description of the assumption.
+     * @throws RuntimeException if the assertion isn't valid.
+     */
+    public static void assertNull(Object o, String msg) {
+        assertEquals(o, null, msg);
+    }
+
+    /**
+     * Calls {@link #assertNotNull(Object, String)} with a default message.
+     *
+     * @see #assertNotNull(Object, String)
+     */
+    public static void assertNotNull(Object o) {
+        assertNotNull(o, "Expected non null reference");
+    }
+
+    /**
+     * Asserts that {@code o} is <i>not</i> null.
+     *
+     * @param o The reference assumed <i>not</i> to be null,
+     * @param msg A description of the assumption.
+     * @throws RuntimeException if the assertion isn't valid.
+     */
+    public static void assertNotNull(Object o, String msg) {
+        assertNotEquals(o, null, msg);
+    }
+
+    /**
+     * Calls {@link #assertFalse(boolean, String)} with a default message.
+     *
+     * @see #assertFalse(boolean, String)
+     */
+    public static void assertFalse(boolean value) {
+        assertFalse(value, "Expected value to be false");
+    }
+
+    /**
+     * Asserts that {@code value} is {@code false}.
+     *
+     * @param value The value assumed to be false.
+     * @param msg A description of the assumption.
+     * @throws RuntimeException if the assertion isn't valid.
+     */
+    public static void assertFalse(boolean value, String msg) {
+        assertTrue(!value, msg);
+    }
+
+    /**
+     * Calls {@link #assertTrue(boolean, String)} with a default message.
+     *
+     * @see #assertTrue(boolean, String)
+     */
+    public static void assertTrue(boolean value) {
+        assertTrue(value, "Expected value to be true");
+    }
+
+    /**
+     * Asserts that {@code value} is {@code true}.
+     *
+     * @param value The value assumed to be true.
+     * @param msg A description of the assumption.
+     * @throws RuntimeException if the assertion isn't valid.
+     */
+    public static void assertTrue(boolean value, String msg) {
+        if (!value) {
+            error(msg);
+        }
+    }
+
+    /**
+     * Asserts that two strings are equal.
+     *
+     * If strings are not equals, then exception message
+     * will contain {@code msg} followed by list of mismatched lines.
+     *
+     * @param str1 First string to compare.
+     * @param str2 Second string to compare.
+     * @param msg A description of the assumption.
+     * @throws RuntimeException if strings are not equal.
+     */
+    public static void assertStringsEqual(String str1, String str2,
+                                          String msg) {
+        String lineSeparator = System.getProperty("line.separator");
+        String str1Lines[] = str1.split(lineSeparator);
+        String str2Lines[] = str2.split(lineSeparator);
+
+        int minLength = Math.min(str1Lines.length, str2Lines.length);
+        String longestStringLines[] = ((str1Lines.length == minLength) ?
+                                       str2Lines : str1Lines);
+
+        boolean stringsAreDifferent = false;
+
+        StringBuilder messageBuilder = new StringBuilder(msg);
+
+        messageBuilder.append("\n");
+
+        for (int line = 0; line < minLength; line++) {
+            if (!str1Lines[line].equals(str2Lines[line])) {
+                messageBuilder.append(String.
+                                      format("[line %d] '%s' differs " +
+                                             "from '%s'\n",
+                                             line,
+                                             str1Lines[line],
+                                             str2Lines[line]));
+                stringsAreDifferent = true;
+            }
+        }
+
+        if (minLength < longestStringLines.length) {
+            String stringName = ((longestStringLines == str1Lines) ?
+                                 "first" : "second");
+            messageBuilder.append(String.format("Only %s string contains " +
+                                                "following lines:\n",
+                                                stringName));
+            stringsAreDifferent = true;
+            for(int line = minLength; line < longestStringLines.length; line++) {
+                messageBuilder.append(String.
+                                      format("[line %d] '%s'", line,
+                                             longestStringLines[line]));
+            }
+        }
+
+        if (stringsAreDifferent) {
+            error(messageBuilder.toString());
+        }
+    }
+
+    private static <T extends Comparable<T>> int compare(T lhs, T rhs, String msg) {
+        assertNotNull(lhs, msg);
+        assertNotNull(rhs, msg);
+        return lhs.compareTo(rhs);
+    }
+
+    private static String format(Object o) {
+        return o == null? "null" : o.toString();
+    }
+
+    private static void error(String msg) {
+        throw new RuntimeException(msg);
+    }
+
+    private static String getMessage(Object lhs, Object rhs, String op, String msg) {
+        return (msg == null ? "" : msg + " ") + "(assert failed: " + format(lhs) + " " + op +  " " + format(rhs) + ")";
+    }
+}
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/BuildHelper.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,106 @@
+/*
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib;
+
+import java.io.File;
+import java.io.FileReader;
+import java.util.Properties;
+
+public class BuildHelper {
+
+    /**
+     * Commercial builds should have the BUILD_TYPE set to commercial
+     * within the release file, found at the root of the JDK.
+     */
+    public static boolean isCommercialBuild() throws Exception {
+        String buildType = getReleaseProperty("BUILD_TYPE","notFound");
+        return buildType.equals("commercial");
+    }
+
+
+    /**
+     * Return the value for property key, or defaultValue if no property not found.
+     * If present, double quotes are trimmed.
+     */
+    public static String getReleaseProperty(String key, String defaultValue) throws Exception {
+        Properties properties = getReleaseProperties();
+        String value = properties.getProperty(key, defaultValue);
+        return trimDoubleQuotes(value);
+    }
+
+    /**
+     * Return the value for property key, or null if no property not found.
+     * If present, double quotes are trimmed.
+     */
+    public static String getReleaseProperty(String key) throws Exception {
+        return getReleaseProperty(key, null);
+    }
+
+    /**
+     * Get properties from the release file
+     */
+    public static Properties getReleaseProperties() throws Exception {
+        Properties properties = new Properties();
+        properties.load(new FileReader(getReleaseFile()));
+        return properties;
+    }
+
+    /**
+     * Every JDK has a release file in its root.
+     * @return A handler to the release file.
+     */
+    public static File getReleaseFile() throws Exception {
+        String jdkPath = getJDKRoot();
+        File releaseFile = new File(jdkPath,"release");
+        if ( ! releaseFile.canRead() ) {
+            throw new Exception("Release file is not readable, or it is absent: " +
+                    releaseFile.getCanonicalPath());
+        }
+        return releaseFile;
+    }
+
+    /**
+     * Returns path to the JDK under test.
+     * This path is obtained through the test.jdk property, usually set by JTREG.
+     */
+    public static String getJDKRoot() {
+        String jdkPath = System.getProperty("test.jdk");
+        if (jdkPath == null) {
+            throw new RuntimeException("System property 'test.jdk' not set. This property is normally set by jtreg. "
+                    + "When running test separately, set this property using '-Dtest.jdk=/path/to/jdk'.");
+        }
+        return jdkPath;
+    }
+
+    /**
+     * Trim double quotes from the beginning and the end of the given string.
+     * @param original string to trim.
+     * @return a new trimmed string.
+     */
+    public static String trimDoubleQuotes(String original) {
+        if (original == null) { return null; }
+        String trimmed = original.replaceAll("^\"+|\"+$", "");
+        return trimmed;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/ByteCodeLoader.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,90 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib;
+
+import java.security.SecureClassLoader;
+
+/**
+ * {@code ByteCodeLoader} can be used for easy loading of byte code already
+ * present in memory.
+ *
+ * {@code InMemoryCompiler} can be used for compiling source code in a string
+ * into byte code, which then can be loaded with {@code ByteCodeLoader}.
+ *
+ * @see InMemoryCompiler
+ */
+public class ByteCodeLoader extends SecureClassLoader {
+    private final String className;
+    private final byte[] byteCode;
+    private volatile Class<?> holder;
+
+    /**
+     * Creates a new {@code ByteCodeLoader} ready to load a class with the
+     * given name and the given byte code.
+     *
+     * @param className The name of the class
+     * @param byteCode The byte code of the class
+     */
+    public ByteCodeLoader(String className, byte[] byteCode) {
+        this.className = className;
+        this.byteCode = byteCode;
+    }
+
+    @Override
+    public Class<?> loadClass(String name) throws ClassNotFoundException {
+        if (!name.equals(className)) {
+            return super.loadClass(name);
+        }
+        if (holder == null) {
+            synchronized(this) {
+                if (holder == null) {
+                    holder = findClass(name);
+                }
+            }
+        }
+        return holder;
+    }
+
+    @Override
+    protected Class<?> findClass(String name) throws ClassNotFoundException {
+        if (!name.equals(className)) {
+            throw new ClassNotFoundException(name);
+        }
+
+        return defineClass(name, byteCode, 0, byteCode.length);
+    }
+
+    /**
+     * Utility method for creating a new {@code ByteCodeLoader} and then
+     * directly load the given byte code.
+     *
+     * @param className The name of the class
+     * @param byteCode The byte code for the class
+     * @throws ClassNotFoundException if the class can't be loaded
+     * @return A {@see Class} object representing the class
+     */
+    public static Class<?> load(String className, byte[] byteCode) throws ClassNotFoundException {
+        return new ByteCodeLoader(className, byteCode).loadClass(className);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/DynamicVMOption.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,165 @@
+/*
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.test.lib;
+
+import com.sun.management.HotSpotDiagnosticMXBean;
+import java.lang.management.ManagementFactory;
+
+/**
+ * A utility class to work with VM options which could be altered during
+ * execution.
+ *
+ * This class is a wrapper around {@code com.sun.management.VMOption}.
+ * It provides more convenient interface to read/write the values.
+ *
+ */
+public class DynamicVMOption {
+
+    private final HotSpotDiagnosticMXBean mxBean;
+
+    /**
+     * VM option name, like "MinHeapFreeRatio".
+     */
+    public final String name;
+
+    /**
+     * Creates an instance of DynamicVMOption.
+     *
+     * @param name the VM option name
+     */
+    public DynamicVMOption(String name) {
+        this.name = name;
+        mxBean = ManagementFactory.getPlatformMXBean(HotSpotDiagnosticMXBean.class);
+    }
+
+    /**
+     * Sets a new value for the option.
+     * Trying to set not applicable value will cause IllegalArgumentException.
+     * Behavior with null is undefined, most likely NPE will be thrown.
+     *
+     * @param newValue the value to be set
+     * @see #getValue()
+     * @throws IllegalArgumentException if newValue is not applicable to the option
+     */
+    public final void setValue(String newValue) {
+        mxBean.setVMOption(name, newValue);
+    }
+
+    /**
+     * Returns the value of option.
+     *
+     * @return the current option value
+     * @see #setValue(java.lang.String)
+     */
+    public final String getValue() {
+        return mxBean.getVMOption(name).getValue();
+    }
+
+    /**
+     * Returns true, if option is writable, false otherwise.
+     *
+     * @return true, if option is writable, false otherwise
+     */
+    public final boolean isWriteable() {
+        return mxBean.getVMOption(name).isWriteable();
+    }
+
+    /**
+     * Checks if the given value is applicable for the option.
+     *
+     * This method tries to set the option to the new value. If no exception
+     * has been thrown the value is treated as valid.
+     *
+     * Calling this method will not change the option value. After an attempt
+     * to set a new value, the option will be restored to its previous value.
+     *
+     * @param value the value to verify
+     * @return true if option could be set to the given value
+     */
+    public boolean isValidValue(String value) {
+        boolean isValid = true;
+        String oldValue = getValue();
+        try {
+            setValue(value);
+        } catch (NullPointerException e) {
+            if (value == null) {
+                isValid = false;
+            }
+        } catch (IllegalArgumentException e) {
+            isValid = false;
+        } finally {
+            setValue(oldValue);
+        }
+        return isValid;
+    }
+
+    /**
+     * Returns the value of the given VM option as String.
+     *
+     * This is a simple shortcut for {@code new DynamicVMOption(name).getValue()}
+     *
+     * @param name the name of VM option
+     * @return value as a string
+     * @see #getValue()
+     */
+    public static String getString(String name) {
+        return new DynamicVMOption(name).getValue();
+    }
+
+    /**
+     * Returns the value of the given option as int.
+     *
+     * @param name the name of VM option
+     * @return value parsed as integer
+     * @see #getString(java.lang.String)
+     *
+     */
+    public static int getInt(String name) {
+        return Integer.parseInt(getString(name));
+    }
+
+    /**
+     * Sets the VM option to a new value.
+     *
+     * This is a simple shortcut for {@code new DynamicVMOption(name).setValue(value)}
+     *
+     * @param name the name of VM option
+     * @param value the value to be set
+     * @see #setValue(java.lang.String)
+     */
+    public static void setString(String name, String value) {
+        new DynamicVMOption(name).setValue(value);
+    }
+
+    /**
+     * Sets the VM option value to a new integer value.
+     *
+     * @param name the name of VM option
+     * @param value the integer value to be set
+     * @see #setString(java.lang.String, java.lang.String)
+     */
+    public static void setInt(String name, int value) {
+        new DynamicVMOption(name).setValue(Integer.toString(value));
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/ExitCode.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,40 @@
+/*
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib;
+
+/**
+ * Exit code values that could be returned by the JVM.
+ */
+public enum ExitCode {
+    OK(0),
+    FAIL(1),
+    CRASH(134);
+
+    public final int value;
+
+    ExitCode(int value) {
+        this.value = value;
+    }
+}
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/InMemoryJavaCompiler.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,154 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib;
+
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+import java.io.OutputStream;
+
+import java.net.URI;
+import java.util.Arrays;
+
+import javax.tools.ForwardingJavaFileManager;
+import javax.tools.ForwardingJavaFileManager;
+import javax.tools.FileObject;
+import javax.tools.JavaCompiler;
+import javax.tools.JavaCompiler.CompilationTask;
+import javax.tools.JavaFileManager;
+import javax.tools.JavaFileObject;
+import javax.tools.JavaFileObject.Kind;
+import javax.tools.SimpleJavaFileObject;
+import javax.tools.ToolProvider;
+
+/**
+ * {@code InMemoryJavaCompiler} can be used for compiling a {@link
+ * CharSequence} to a {@code byte[]}.
+ *
+ * The compiler will not use the file system at all, instead using a {@link
+ * ByteArrayOutputStream} for storing the byte code. For the source code, any
+ * kind of {@link CharSequence} can be used, e.g. {@link String}, {@link
+ * StringBuffer} or {@link StringBuilder}.
+ *
+ * The {@code InMemoryCompiler} can easily be used together with a {@code
+ * ByteClassLoader} to easily compile and load source code in a {@link String}:
+ *
+ * <pre>
+ * {@code
+ * import jdk.test.lib.InMemoryJavaCompiler;
+ * import jdk.test.lib.ByteClassLoader;
+ *
+ * class Example {
+ *     public static void main(String[] args) {
+ *         String className = "Foo";
+ *         String sourceCode = "public class " + className + " {" +
+ *                             "    public void bar() {" +
+ *                             "        System.out.println("Hello from bar!");" +
+ *                             "    }" +
+ *                             "}";
+ *         byte[] byteCode = InMemoryJavaCompiler.compile(className, sourceCode);
+ *         Class fooClass = ByteClassLoader.load(className, byteCode);
+ *     }
+ * }
+ * }
+ * </pre>
+ */
+public class InMemoryJavaCompiler {
+    private static class MemoryJavaFileObject extends SimpleJavaFileObject {
+        private final String className;
+        private final CharSequence sourceCode;
+        private final ByteArrayOutputStream byteCode;
+
+        public MemoryJavaFileObject(String className, CharSequence sourceCode) {
+            super(URI.create("string:///" + className.replace('.','/') + Kind.SOURCE.extension), Kind.SOURCE);
+            this.className = className;
+            this.sourceCode = sourceCode;
+            this.byteCode = new ByteArrayOutputStream();
+        }
+
+        @Override
+        public CharSequence getCharContent(boolean ignoreEncodingErrors) {
+            return sourceCode;
+        }
+
+        @Override
+        public OutputStream openOutputStream() throws IOException {
+            return byteCode;
+        }
+
+        public byte[] getByteCode() {
+            return byteCode.toByteArray();
+        }
+
+        public String getClassName() {
+            return className;
+        }
+    }
+
+    private static class FileManagerWrapper extends ForwardingJavaFileManager {
+        private MemoryJavaFileObject file;
+
+        public FileManagerWrapper(MemoryJavaFileObject file) {
+            super(getCompiler().getStandardFileManager(null, null, null));
+            this.file = file;
+        }
+
+        @Override
+        public JavaFileObject getJavaFileForOutput(Location location, String className,
+                                                   Kind kind, FileObject sibling)
+            throws IOException {
+            if (!file.getClassName().equals(className)) {
+                throw new IOException("Expected class with name " + file.getClassName() +
+                                      ", but got " + className);
+            }
+            return file;
+        }
+    }
+
+    /**
+     * Compiles the class with the given name and source code.
+     *
+     * @param className The name of the class
+     * @param sourceCode The source code for the class with name {@code className}
+     * @throws RuntimeException if the compilation did not succeed
+     * @return The resulting byte code from the compilation
+     */
+    public static byte[] compile(String className, CharSequence sourceCode) {
+        MemoryJavaFileObject file = new MemoryJavaFileObject(className, sourceCode);
+        CompilationTask task = getCompilationTask(file);
+
+        if(!task.call()) {
+            throw new RuntimeException("Could not compile " + className + " with source code " + sourceCode);
+        }
+
+        return file.getByteCode();
+    }
+
+    private static JavaCompiler getCompiler() {
+        return ToolProvider.getSystemJavaCompiler();
+    }
+
+    private static CompilationTask getCompilationTask(MemoryJavaFileObject file) {
+        return getCompiler().getTask(null, new FileManagerWrapper(file), null, null, null, Arrays.asList(file));
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/InfiniteLoop.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,66 @@
+/*
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib;
+
+import java.util.Objects;
+
+/**
+ * Class which runs another Runnable in infinite loop with certain pauses
+ * between cycles.
+ */
+public class InfiniteLoop implements Runnable {
+    private final Runnable target;
+    private final long mills;
+
+
+    /**
+     * @param target a target to run in a loop
+     * @param mills  the length of pause time in milliseconds
+     * @throws NullPointerException if target is null
+     * @throws IllegalArgumentException if the value of millis is negative
+     */
+    public InfiniteLoop(Runnable target, long mills) {
+        Objects.requireNonNull(target);
+        if (mills < 0) {
+            throw new IllegalArgumentException("mills < 0");
+        }
+        this.target = target;
+        this.mills = mills;
+    }
+
+    @Override
+    public void run() {
+        try {
+            while (true) {
+                target.run();
+                if (mills > 0) {
+                    Thread.sleep(mills);
+                }
+            }
+        } catch (InterruptedException e) {
+            Thread.currentThread().interrupt();
+            throw new Error(e);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/InputArguments.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,76 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib;
+
+import java.lang.management.RuntimeMXBean;
+import java.lang.management.ManagementFactory;
+import java.util.List;
+
+/**
+ * This class provides access to the input arguments to the VM.
+ */
+public class InputArguments {
+    private static final List<String> args;
+
+    static {
+        RuntimeMXBean runtimeMxBean = ManagementFactory.getRuntimeMXBean();
+        args = runtimeMxBean.getInputArguments();
+    }
+
+    /**
+     * Returns true if {@code arg} is an input argument to the VM.
+     *
+     * This is useful for checking boolean flags such as -XX:+UseSerialGC or
+     * -XX:-UsePerfData.
+     *
+     * @param arg The name of the argument.
+     * @return {@code true} if the given argument is an input argument,
+     *         otherwise {@code false}.
+     */
+    public static boolean contains(String arg) {
+        return args.contains(arg);
+    }
+
+    /**
+     * Returns true if {@code prefix} is the start of an input argument to the
+     * VM.
+     *
+     * This is useful for checking if flags describing a quantity, such as
+     * -XX:+MaxMetaspaceSize=100m, is set without having to know the quantity.
+     * To check if the flag -XX:MaxMetaspaceSize is set, use
+     * {@code InputArguments.containsPrefix("-XX:MaxMetaspaceSize")}.
+     *
+     * @param prefix The start of the argument.
+     * @return {@code true} if the given argument is the start of an input
+     *         argument, otherwise {@code false}.
+     */
+    public static boolean containsPrefix(String prefix) {
+        for (String arg : args) {
+            if (arg.startsWith(prefix)) {
+                return true;
+            }
+        }
+        return false;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/JDKToolFinder.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,106 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib;
+
+import java.io.FileNotFoundException;
+import java.nio.file.Path;
+import java.nio.file.Paths;
+
+public final class JDKToolFinder {
+
+    private JDKToolFinder() {
+    }
+
+    /**
+     * Returns the full path to an executable in jdk/bin based on System
+     * property {@code test.jdk} or {@code compile.jdk} (both are set by the jtreg test suite)
+     *
+     * @return Full path to an executable in jdk/bin
+     */
+    public static String getJDKTool(String tool) {
+
+        // First try to find the executable in test.jdk
+        try {
+            return getTool(tool, "test.jdk");
+        } catch (FileNotFoundException e) {
+
+        }
+
+        // Now see if it's available in compile.jdk
+        try {
+            return getTool(tool, "compile.jdk");
+        } catch (FileNotFoundException e) {
+            throw new RuntimeException("Failed to find " + tool +
+                    ", looked in test.jdk (" + System.getProperty("test.jdk") +
+                    ") and compile.jdk (" + System.getProperty("compile.jdk") + ")");
+        }
+    }
+
+    /**
+     * Returns the full path to an executable in jdk/bin based on System
+     * property {@code compile.jdk}
+     *
+     * @return Full path to an executable in jdk/bin
+     */
+    public static String getCompileJDKTool(String tool) {
+        try {
+            return getTool(tool, "compile.jdk");
+        } catch (FileNotFoundException e) {
+            throw new RuntimeException(e);
+        }
+    }
+
+    /**
+     * Returns the full path to an executable in jdk/bin based on System
+     * property {@code test.jdk}
+     *
+     * @return Full path to an executable in jdk/bin
+     */
+    public static String getTestJDKTool(String tool) {
+        try {
+            return getTool(tool, "test.jdk");
+        } catch (FileNotFoundException e) {
+            throw new RuntimeException(e);
+        }
+    }
+
+    private static String getTool(String tool, String property) throws FileNotFoundException {
+        String jdkPath = System.getProperty(property);
+
+        if (jdkPath == null) {
+            throw new RuntimeException(
+                    "System property '" + property + "' not set. This property is normally set by jtreg. "
+                    + "When running test separately, set this property using '-D" + property + "=/path/to/jdk'.");
+        }
+
+        Path toolName = Paths.get("bin", tool + (Platform.isWindows() ? ".exe" : ""));
+
+        Path jdkTool = Paths.get(jdkPath, toolName.toString());
+        if (!jdkTool.toFile().exists()) {
+            throw new FileNotFoundException("Could not find file " + jdkTool.toAbsolutePath());
+        }
+
+        return jdkTool.toAbsolutePath().toString();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/JDKToolLauncher.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,134 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+
+/**
+ * A utility for constructing command lines for starting JDK tool processes.
+ *
+ * The JDKToolLauncher can in particular be combined with a
+ * java.lang.ProcessBuilder to easily run a JDK tool. For example, the following
+ * code run {@code jmap -heap} against a process with GC logging turned on for
+ * the {@code jmap} process:
+ *
+ * <pre>
+ * {@code
+ * JDKToolLauncher jmap = JDKToolLauncher.create("jmap")
+ *                                       .addVMArg("-XX:+PrintGC");
+ *                                       .addVMArg("-XX:+PrintGCDetails")
+ *                                       .addToolArg("-heap")
+ *                                       .addToolArg(pid);
+ * ProcessBuilder pb = new ProcessBuilder(jmap.getCommand());
+ * Process p = pb.start();
+ * }
+ * </pre>
+ */
+public class JDKToolLauncher {
+    private final String executable;
+    private final List<String> vmArgs = new ArrayList<String>();
+    private final List<String> toolArgs = new ArrayList<String>();
+
+    private JDKToolLauncher(String tool, boolean useCompilerJDK) {
+        if (useCompilerJDK) {
+            executable = JDKToolFinder.getJDKTool(tool);
+        } else {
+            executable = JDKToolFinder.getTestJDKTool(tool);
+        }
+        vmArgs.addAll(Arrays.asList(ProcessTools.getPlatformSpecificVMArgs()));
+    }
+
+    /**
+     * Creates a new JDKToolLauncher for the specified tool. Using tools path
+     * from the compiler JDK.
+     *
+     * @param tool
+     *            The name of the tool
+     * @return A new JDKToolLauncher
+     */
+    public static JDKToolLauncher create(String tool) {
+        return new JDKToolLauncher(tool, true);
+    }
+
+    /**
+     * Creates a new JDKToolLauncher for the specified tool in the Tested JDK.
+     *
+     * @param tool
+     *            The name of the tool
+     *
+     * @return A new JDKToolLauncher
+     */
+    public static JDKToolLauncher createUsingTestJDK(String tool) {
+        return new JDKToolLauncher(tool, false);
+    }
+
+    /**
+     * Adds an argument to the JVM running the tool.
+     *
+     * The JVM arguments are passed to the underlying JVM running the tool.
+     * Arguments will automatically be prepended with "-J".
+     *
+     * Any platform specific arguments required for running the tool are
+     * automatically added.
+     *
+     *
+     * @param arg
+     *            The argument to VM running the tool
+     * @return The JDKToolLauncher instance
+     */
+    public JDKToolLauncher addVMArg(String arg) {
+        vmArgs.add(arg);
+        return this;
+    }
+
+    /**
+     * Adds an argument to the tool.
+     *
+     * @param arg
+     *            The argument to the tool
+     * @return The JDKToolLauncher instance
+     */
+    public JDKToolLauncher addToolArg(String arg) {
+        toolArgs.add(arg);
+        return this;
+    }
+
+    /**
+     * Returns the command that can be used for running the tool.
+     *
+     * @return An array whose elements are the arguments of the command.
+     */
+    public String[] getCommand() {
+        List<String> command = new ArrayList<String>();
+        command.add(executable);
+        // Add -J in front of all vmArgs
+        for (String arg : vmArgs) {
+            command.add("-J" + arg);
+        }
+        command.addAll(toolArgs);
+        return command.toArray(new String[command.size()]);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/OutputAnalyzer.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,436 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib;
+
+import java.io.IOException;
+import java.util.Arrays;
+import java.util.List;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+public final class OutputAnalyzer {
+
+  private final String stdout;
+  private final String stderr;
+  private final int exitValue;
+
+  /**
+   * Create an OutputAnalyzer, a utility class for verifying output and exit
+   * value from a Process
+   *
+   * @param process Process to analyze
+   * @throws IOException If an I/O error occurs.
+   */
+  public OutputAnalyzer(Process process) throws IOException {
+    OutputBuffer output = ProcessTools.getOutput(process);
+    exitValue = process.exitValue();
+    this.stdout = output.getStdout();
+    this.stderr = output.getStderr();
+  }
+
+  /**
+   * Create an OutputAnalyzer, a utility class for verifying output
+   *
+   * @param buf String buffer to analyze
+   */
+  public OutputAnalyzer(String buf) {
+    this(buf, buf);
+  }
+
+  /**
+   * Create an OutputAnalyzer, a utility class for verifying output
+   *
+   * @param stdout stdout buffer to analyze
+   * @param stderr stderr buffer to analyze
+   */
+  public OutputAnalyzer(String stdout, String stderr) {
+    this.stdout = stdout;
+    this.stderr = stderr;
+    exitValue = -1;
+  }
+
+  /**
+   * Verify that the stdout contents of output buffer is empty
+   *
+   * @throws RuntimeException
+   *             If stdout was not empty
+   */
+  public void stdoutShouldBeEmpty() {
+    if (!getStdout().isEmpty()) {
+      reportDiagnosticSummary();
+      throw new RuntimeException("stdout was not empty");
+    }
+  }
+
+  /**
+   * Verify that the stderr contents of output buffer is empty
+   *
+   * @throws RuntimeException
+   *             If stderr was not empty
+   */
+  public void stderrShouldBeEmpty() {
+    if (!getStderr().isEmpty()) {
+      reportDiagnosticSummary();
+      throw new RuntimeException("stderr was not empty");
+    }
+  }
+
+  /**
+   * Verify that the stdout contents of output buffer is not empty
+   *
+   * @throws RuntimeException
+   *             If stdout was empty
+   */
+  public void stdoutShouldNotBeEmpty() {
+    if (getStdout().isEmpty()) {
+      reportDiagnosticSummary();
+      throw new RuntimeException("stdout was empty");
+    }
+  }
+
+  /**
+   * Verify that the stderr contents of output buffer is not empty
+   *
+   * @throws RuntimeException
+   *             If stderr was empty
+   */
+  public void stderrShouldNotBeEmpty() {
+    if (getStderr().isEmpty()) {
+      reportDiagnosticSummary();
+      throw new RuntimeException("stderr was empty");
+    }
+  }
+
+    /**
+   * Verify that the stdout and stderr contents of output buffer contains the string
+   *
+   * @param expectedString String that buffer should contain
+   * @throws RuntimeException If the string was not found
+   */
+  public OutputAnalyzer shouldContain(String expectedString) {
+    if (!stdout.contains(expectedString) && !stderr.contains(expectedString)) {
+        reportDiagnosticSummary();
+        throw new RuntimeException("'" + expectedString + "' missing from stdout/stderr \n");
+    }
+    return this;
+  }
+
+  /**
+   * Verify that the stdout contents of output buffer contains the string
+   *
+   * @param expectedString String that buffer should contain
+   * @throws RuntimeException If the string was not found
+   */
+  public OutputAnalyzer stdoutShouldContain(String expectedString) {
+    if (!stdout.contains(expectedString)) {
+        reportDiagnosticSummary();
+        throw new RuntimeException("'" + expectedString + "' missing from stdout \n");
+    }
+    return this;
+  }
+
+  /**
+   * Verify that the stderr contents of output buffer contains the string
+   *
+   * @param expectedString String that buffer should contain
+   * @throws RuntimeException If the string was not found
+   */
+  public OutputAnalyzer stderrShouldContain(String expectedString) {
+    if (!stderr.contains(expectedString)) {
+        reportDiagnosticSummary();
+        throw new RuntimeException("'" + expectedString + "' missing from stderr \n");
+    }
+    return this;
+  }
+
+  /**
+   * Verify that the stdout and stderr contents of output buffer does not contain the string
+   *
+   * @param expectedString String that the buffer should not contain
+   * @throws RuntimeException If the string was found
+   */
+  public OutputAnalyzer shouldNotContain(String notExpectedString) {
+    if (stdout.contains(notExpectedString)) {
+        reportDiagnosticSummary();
+        throw new RuntimeException("'" + notExpectedString + "' found in stdout \n");
+    }
+    if (stderr.contains(notExpectedString)) {
+        reportDiagnosticSummary();
+        throw new RuntimeException("'" + notExpectedString + "' found in stderr \n");
+    }
+    return this;
+  }
+
+  /**
+   * Verify that the stdout contents of output buffer does not contain the string
+   *
+   * @param expectedString String that the buffer should not contain
+   * @throws RuntimeException If the string was found
+   */
+  public OutputAnalyzer stdoutShouldNotContain(String notExpectedString) {
+    if (stdout.contains(notExpectedString)) {
+        reportDiagnosticSummary();
+        throw new RuntimeException("'" + notExpectedString + "' found in stdout \n");
+    }
+    return this;
+  }
+
+  /**
+   * Verify that the stderr contents of output buffer does not contain the string
+   *
+   * @param expectedString String that the buffer should not contain
+   * @throws RuntimeException If the string was found
+   */
+  public OutputAnalyzer stderrShouldNotContain(String notExpectedString) {
+    if (stderr.contains(notExpectedString)) {
+        reportDiagnosticSummary();
+        throw new RuntimeException("'" + notExpectedString + "' found in stderr \n");
+    }
+    return this;
+  }
+
+  /**
+   * Verify that the stdout and stderr contents of output buffer matches
+   * the pattern
+   *
+   * @param pattern
+   * @throws RuntimeException If the pattern was not found
+   */
+  public OutputAnalyzer shouldMatch(String pattern) {
+      Matcher stdoutMatcher = Pattern.compile(pattern, Pattern.MULTILINE).matcher(stdout);
+      Matcher stderrMatcher = Pattern.compile(pattern, Pattern.MULTILINE).matcher(stderr);
+      if (!stdoutMatcher.find() && !stderrMatcher.find()) {
+          reportDiagnosticSummary();
+          throw new RuntimeException("'" + pattern
+                + "' missing from stdout/stderr \n");
+      }
+      return this;
+  }
+
+  /**
+   * Verify that the stdout contents of output buffer matches the
+   * pattern
+   *
+   * @param pattern
+   * @throws RuntimeException If the pattern was not found
+   */
+  public OutputAnalyzer stdoutShouldMatch(String pattern) {
+      Matcher matcher = Pattern.compile(pattern, Pattern.MULTILINE).matcher(stdout);
+      if (!matcher.find()) {
+          reportDiagnosticSummary();
+          throw new RuntimeException("'" + pattern
+                + "' missing from stdout \n");
+      }
+      return this;
+  }
+
+  /**
+   * Verify that the stderr contents of output buffer matches the
+   * pattern
+   *
+   * @param pattern
+   * @throws RuntimeException If the pattern was not found
+   */
+  public OutputAnalyzer stderrShouldMatch(String pattern) {
+      Matcher matcher = Pattern.compile(pattern, Pattern.MULTILINE).matcher(stderr);
+      if (!matcher.find()) {
+          reportDiagnosticSummary();
+          throw new RuntimeException("'" + pattern
+                + "' missing from stderr \n");
+      }
+      return this;
+  }
+
+  /**
+   * Verify that the stdout and stderr contents of output buffer does not
+   * match the pattern
+   *
+   * @param pattern
+   * @throws RuntimeException If the pattern was found
+   */
+  public OutputAnalyzer shouldNotMatch(String pattern) {
+      Matcher matcher = Pattern.compile(pattern, Pattern.MULTILINE).matcher(stdout);
+      if (matcher.find()) {
+          reportDiagnosticSummary();
+          throw new RuntimeException("'" + pattern
+                  + "' found in stdout: '" + matcher.group() + "' \n");
+      }
+      matcher = Pattern.compile(pattern, Pattern.MULTILINE).matcher(stderr);
+      if (matcher.find()) {
+          reportDiagnosticSummary();
+          throw new RuntimeException("'" + pattern
+                  + "' found in stderr: '" + matcher.group() + "' \n");
+      }
+      return this;
+  }
+
+  /**
+   * Verify that the stdout contents of output buffer does not match the
+   * pattern
+   *
+   * @param pattern
+   * @throws RuntimeException If the pattern was found
+   */
+  public OutputAnalyzer stdoutShouldNotMatch(String pattern) {
+      Matcher matcher = Pattern.compile(pattern, Pattern.MULTILINE).matcher(stdout);
+      if (matcher.find()) {
+          reportDiagnosticSummary();
+          throw new RuntimeException("'" + pattern
+                  + "' found in stdout \n");
+      }
+      return this;
+  }
+
+  /**
+   * Verify that the stderr contents of output buffer does not match the
+   * pattern
+   *
+   * @param pattern
+   * @throws RuntimeException If the pattern was found
+   */
+  public OutputAnalyzer stderrShouldNotMatch(String pattern) {
+      Matcher matcher = Pattern.compile(pattern, Pattern.MULTILINE).matcher(stderr);
+      if (matcher.find()) {
+          reportDiagnosticSummary();
+          throw new RuntimeException("'" + pattern
+                  + "' found in stderr \n");
+      }
+      return this;
+  }
+
+  /**
+   * Get the captured group of the first string matching the pattern.
+   * stderr is searched before stdout.
+   *
+   * @param pattern The multi-line pattern to match
+   * @param group The group to capture
+   * @return The matched string or null if no match was found
+   */
+  public String firstMatch(String pattern, int group) {
+    Matcher stderrMatcher = Pattern.compile(pattern, Pattern.MULTILINE).matcher(stderr);
+    Matcher stdoutMatcher = Pattern.compile(pattern, Pattern.MULTILINE).matcher(stdout);
+    if (stderrMatcher.find()) {
+      return stderrMatcher.group(group);
+    }
+    if (stdoutMatcher.find()) {
+      return stdoutMatcher.group(group);
+    }
+    return null;
+  }
+
+  /**
+   * Get the first string matching the pattern.
+   * stderr is searched before stdout.
+   *
+   * @param pattern The multi-line pattern to match
+   * @return The matched string or null if no match was found
+   */
+  public String firstMatch(String pattern) {
+    return firstMatch(pattern, 0);
+  }
+
+  /**
+   * Verify the exit value of the process
+   *
+   * @param expectedExitValue Expected exit value from process
+   * @throws RuntimeException If the exit value from the process did not match the expected value
+   */
+  public OutputAnalyzer shouldHaveExitValue(int expectedExitValue) {
+      if (getExitValue() != expectedExitValue) {
+          reportDiagnosticSummary();
+          throw new RuntimeException("Expected to get exit value of ["
+                  + expectedExitValue + "]\n");
+      }
+      return this;
+  }
+
+
+  /**
+   * Report summary that will help to diagnose the problem
+   * Currently includes:
+   *  - standard input produced by the process under test
+   *  - standard output
+   *  - exit code
+   *  Note: the command line is printed by the ProcessTools
+   */
+    private void reportDiagnosticSummary() {
+        String msg =
+            " stdout: [" + stdout + "];\n" +
+            " stderr: [" + stderr + "]\n" +
+            " exitValue = " + getExitValue() + "\n";
+
+        System.err.println(msg);
+    }
+
+
+  /**
+   * Get the contents of the output buffer (stdout and stderr)
+   *
+   * @return Content of the output buffer
+   */
+  public String getOutput() {
+    return stdout + stderr;
+  }
+
+  /**
+   * Get the contents of the stdout buffer
+   *
+   * @return Content of the stdout buffer
+   */
+  public String getStdout() {
+    return stdout;
+  }
+
+  /**
+   * Get the contents of the stderr buffer
+   *
+   * @return Content of the stderr buffer
+   */
+  public String getStderr() {
+    return stderr;
+  }
+
+  /**
+   * Get the process exit value
+   *
+   * @return Process exit value
+   */
+  public int getExitValue() {
+    return exitValue;
+  }
+
+  /**
+   * Get the contents of the output buffer (stdout and stderr) as list of strings.
+   * Output will be split by newlines.
+   *
+   * @return Contents of the output buffer as list of strings
+   */
+  public List<String> asLines() {
+    return asLines(getOutput());
+  }
+
+  private List<String> asLines(String buffer) {
+    return Arrays.asList(buffer.split("(\\r\\n|\\n|\\r)"));
+  }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/OutputBuffer.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,59 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib;
+
+public class OutputBuffer {
+  private final String stdout;
+  private final String stderr;
+
+  /**
+   * Create an OutputBuffer, a class for storing and managing stdout and stderr
+   * results separately
+   *
+   * @param stdout stdout result
+   * @param stderr stderr result
+   */
+  public OutputBuffer(String stdout, String stderr) {
+    this.stdout = stdout;
+    this.stderr = stderr;
+  }
+
+  /**
+   * Returns the stdout result
+   *
+   * @return stdout result
+   */
+  public String getStdout() {
+    return stdout;
+  }
+
+  /**
+   * Returns the stderr result
+   *
+   * @return stderr result
+   */
+  public String getStderr() {
+    return stderr;
+  }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/PerfCounter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,70 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib;
+
+import sun.jvmstat.monitor.Monitor;
+
+/**
+ * Represents a performance counter in the JVM.
+ *
+ * See http://openjdk.java.net/groups/hotspot/docs/Serviceability.html#bjvmstat
+ * for more details about performance counters.
+ */
+public class PerfCounter {
+    private final Monitor monitor;
+    private final String name;
+
+    PerfCounter(Monitor monitor, String name) {
+        this.monitor = monitor;
+        this.name = name;
+    }
+
+    /**
+     * Returns the value of this performance counter as a long.
+     *
+     * @return The long value of this performance counter
+     * @throws RuntimeException If the value of the performance counter isn't a long
+     */
+    public long longValue() {
+        Object value = monitor.getValue();
+        if (value instanceof Long) {
+            return ((Long) value).longValue();
+        }
+        throw new RuntimeException("Expected " + monitor.getName() + " to have a long value");
+    }
+
+    /**
+     * Returns the name of the performance counter.
+     *
+     * @return The name of the performance counter.
+     */
+    public String getName() {
+        return name;
+    }
+
+    @Override
+    public String toString() {
+        return name;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/PerfCounters.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,69 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib;
+
+import sun.jvmstat.monitor.Monitor;
+import sun.jvmstat.monitor.MonitorException;
+import sun.jvmstat.monitor.MonitoredHost;
+import sun.jvmstat.monitor.MonitoredVm;
+import sun.jvmstat.monitor.VmIdentifier;
+
+/**
+ * PerfCounters can be used to get a performance counter from the currently
+ * executing VM.
+ *
+ * Throws a runtime exception if an error occurs while communicating with the
+ * currently executing VM.
+ */
+public class PerfCounters {
+    private final static MonitoredVm vm;
+
+    static {
+        try {
+            String pid = Integer.toString(ProcessTools.getProcessId());
+            VmIdentifier vmId = new VmIdentifier(pid);
+            MonitoredHost host = MonitoredHost.getMonitoredHost(vmId);
+            vm = host.getMonitoredVm(vmId);
+        } catch (Exception e) {
+            throw new RuntimeException("Could not connect to the VM");
+        }
+    }
+
+    /**
+     * Returns the performance counter with the given name.
+     *
+     * @param name The name of the performance counter.
+     * @throws IllegalArgumentException If no counter with the given name exists.
+     * @throws MonitorException If an error occurs while communicating with the VM.
+     * @return The performance counter with the given name.
+     */
+    public static PerfCounter findByName(String name)
+        throws MonitorException, IllegalArgumentException {
+        Monitor m = vm.findByName(name);
+        if (m == null) {
+            throw new IllegalArgumentException("Did not find a performance counter with name " + name);
+        }
+        return new PerfCounter(m, name);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/Platform.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,199 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib;
+
+import java.util.regex.Pattern;
+import jdk.test.lib.Utils;
+
+public class Platform {
+    private static final String osName      = System.getProperty("os.name");
+    private static final String dataModel   = System.getProperty("sun.arch.data.model");
+    private static final String vmVersion   = System.getProperty("java.vm.version");
+    private static final String javaVersion = System.getProperty("java.version");
+    private static final String osArch      = System.getProperty("os.arch");
+    private static final String vmName      = System.getProperty("java.vm.name");
+    private static final String userName    = System.getProperty("user.name");
+    private static final String compiler    = System.getProperty("sun.management.compiler");
+
+    public static boolean isClient() {
+        return vmName.endsWith(" Client VM");
+    }
+
+    public static boolean isServer() {
+        return vmName.endsWith(" Server VM");
+    }
+
+    public static boolean isGraal() {
+        return vmName.endsWith(" Graal VM");
+    }
+
+    public static boolean isZero() {
+        return vmName.endsWith(" Zero VM");
+    }
+
+    public static boolean isMinimal() {
+        return vmName.endsWith(" Minimal VM");
+    }
+
+    public static boolean isEmbedded() {
+        return vmName.contains("Embedded");
+    }
+
+    public static boolean isTieredSupported() {
+        return compiler.contains("Tiered Compilers");
+    }
+
+    public static boolean is32bit() {
+        return dataModel.equals("32");
+    }
+
+    public static boolean is64bit() {
+        return dataModel.equals("64");
+    }
+
+    public static boolean isAix() {
+        return isOs("aix");
+    }
+
+    public static boolean isLinux() {
+        return isOs("linux");
+    }
+
+    public static boolean isOSX() {
+        return isOs("mac");
+    }
+
+    public static boolean isSolaris() {
+        return isOs("sunos");
+    }
+
+    public static boolean isWindows() {
+        return isOs("win");
+    }
+
+    private static boolean isOs(String osname) {
+        return osName.toLowerCase().startsWith(osname.toLowerCase());
+    }
+
+    public static String getOsName() {
+        return osName;
+    }
+
+    public static boolean isDebugBuild() {
+        return (vmVersion.toLowerCase().contains("debug") ||
+                javaVersion.toLowerCase().contains("debug"));
+    }
+
+    public static String getVMVersion() {
+        return vmVersion;
+    }
+
+    // Returns true for sparc and sparcv9.
+    public static boolean isSparc() {
+        return isArch("sparc.*");
+    }
+
+    public static boolean isARM() {
+        return isArch("arm.*");
+    }
+
+    public static boolean isPPC() {
+        return isArch("ppc.*");
+    }
+
+    public static boolean isX86() {
+        // On Linux it's 'i386', Windows 'x86' without '_64' suffix.
+        return isArch("(i386)|(x86(?!_64))");
+    }
+
+    public static boolean isX64() {
+        // On OSX it's 'x86_64' and on other (Linux, Windows and Solaris) platforms it's 'amd64'
+        return isArch("(amd64)|(x86_64)");
+    }
+
+    private static boolean isArch(String archnameRE) {
+        return Pattern.compile(archnameRE, Pattern.CASE_INSENSITIVE)
+                .matcher(osArch)
+                .matches();
+    }
+
+    public static String getOsArch() {
+        return osArch;
+    }
+
+    /**
+     * Return a boolean for whether we expect to be able to attach
+     * the SA to our own processes on this system.
+     */
+    public static boolean shouldSAAttach() throws Exception {
+
+        if (isAix()) {
+            return false;   // SA not implemented.
+        } else if (isLinux()) {
+            return canPtraceAttachLinux();
+        } else if (isOSX()) {
+            return canAttachOSX();
+        } else {
+            // Other platforms expected to work:
+            return true;
+        }
+    }
+
+    /**
+     * On Linux, first check the SELinux boolean "deny_ptrace" and return false
+     * as we expect to be denied if that is "1".  Then expect permission to attach
+     * if we are root, so return true.  Then return false for an expected denial
+     * if "ptrace_scope" is 1, and true otherwise.
+     */
+    public static boolean canPtraceAttachLinux() throws Exception {
+
+        // SELinux deny_ptrace:
+        String deny_ptrace = Utils.fileAsString("/sys/fs/selinux/booleans/deny_ptrace");
+        if (deny_ptrace != null && deny_ptrace.contains("1")) {
+            // ptrace will be denied:
+            return false;
+        }
+
+        if (userName.equals("root")) {
+            return true;
+        }
+
+        // ptrace_scope:
+        String ptrace_scope = Utils.fileAsString("/proc/sys/kernel/yama/ptrace_scope");
+        if (ptrace_scope != null && ptrace_scope.contains("1")) {
+            // ptrace will be denied:
+            return false;
+        }
+
+        // Otherwise expect to be permitted:
+        return true;
+    }
+
+    /**
+     * On OSX, expect permission to attach only if we are root.
+     */
+    public static boolean canAttachOSX() throws Exception {
+        return userName.equals("root");
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/ProcessTools.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,249 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib;
+
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+import java.lang.management.ManagementFactory;
+import java.lang.management.RuntimeMXBean;
+import java.lang.reflect.Field;
+import java.lang.reflect.Method;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.List;
+
+public final class ProcessTools {
+
+  private ProcessTools() {
+  }
+
+  /**
+   * Pumps stdout and stderr from running the process into a String.
+   *
+   * @param processHandler ProcessHandler to run.
+   * @return Output from process.
+   * @throws IOException If an I/O error occurs.
+   */
+  public static OutputBuffer getOutput(ProcessBuilder processBuilder) throws IOException {
+    return getOutput(processBuilder.start());
+  }
+
+  /**
+   * Pumps stdout and stderr the running process into a String.
+   *
+   * @param process Process to pump.
+   * @return Output from process.
+   * @throws IOException If an I/O error occurs.
+   */
+  public static OutputBuffer getOutput(Process process) throws IOException {
+    ByteArrayOutputStream stderrBuffer = new ByteArrayOutputStream();
+    ByteArrayOutputStream stdoutBuffer = new ByteArrayOutputStream();
+    StreamPumper outPumper = new StreamPumper(process.getInputStream(), stdoutBuffer);
+    StreamPumper errPumper = new StreamPumper(process.getErrorStream(), stderrBuffer);
+    Thread outPumperThread = new Thread(outPumper);
+    Thread errPumperThread = new Thread(errPumper);
+
+    outPumperThread.setDaemon(true);
+    errPumperThread.setDaemon(true);
+
+    outPumperThread.start();
+    errPumperThread.start();
+
+    try {
+      process.waitFor();
+      outPumperThread.join();
+      errPumperThread.join();
+    } catch (InterruptedException e) {
+      Thread.currentThread().interrupt();
+      return null;
+    }
+
+    return new OutputBuffer(stdoutBuffer.toString(), stderrBuffer.toString());
+  }
+
+  /**
+   * Get the process id of the current running Java process
+   *
+   * @return Process id
+   */
+  public static int getProcessId() throws Exception {
+    RuntimeMXBean runtime = ManagementFactory.getRuntimeMXBean();
+    int pid = Integer.parseInt(runtime.getName().split("@")[0]);
+
+    return pid;
+  }
+
+  /**
+   * Get the string containing input arguments passed to the VM
+   *
+   * @return arguments
+   */
+  public static String getVmInputArguments() {
+    RuntimeMXBean runtime = ManagementFactory.getRuntimeMXBean();
+
+    List<String> args = runtime.getInputArguments();
+    StringBuilder result = new StringBuilder();
+    for (String arg : args)
+        result.append(arg).append(' ');
+
+    return result.toString();
+  }
+
+  /**
+   * Get platform specific VM arguments (e.g. -d64 on 64bit Solaris)
+   *
+   * @return String[] with platform specific arguments, empty if there are none
+   */
+  public static String[] getPlatformSpecificVMArgs() {
+
+    if (Platform.is64bit() && Platform.isSolaris()) {
+      return new String[] { "-d64" };
+    }
+
+    return new String[] {};
+  }
+
+  /**
+   * Create ProcessBuilder using the java launcher from the jdk to be tested and
+   * with any platform specific arguments prepended
+   */
+  public static ProcessBuilder createJavaProcessBuilder(String... command) throws Exception {
+    return createJavaProcessBuilder(false, command);
+  }
+
+  public static ProcessBuilder createJavaProcessBuilder(boolean addTestVmAndJavaOptions, String... command) throws Exception {
+    String javapath = JDKToolFinder.getJDKTool("java");
+
+    ArrayList<String> args = new ArrayList<>();
+    args.add(javapath);
+    Collections.addAll(args, getPlatformSpecificVMArgs());
+
+    args.add("-cp");
+    args.add(System.getProperty("java.class.path"));
+
+    if (addTestVmAndJavaOptions) {
+      Collections.addAll(args, Utils.getTestJavaOpts());
+    }
+
+    Collections.addAll(args, command);
+
+    // Reporting
+    StringBuilder cmdLine = new StringBuilder();
+    for (String cmd : args) {
+      cmdLine.append(cmd).append(' ');
+    }
+    System.out.println("Command line: [" + cmdLine.toString() + "]");
+
+    return new ProcessBuilder(args.toArray(new String[args.size()]));
+  }
+
+  /**
+   * Executes a test jvm process, waits for it to finish and returns the process output.
+   * The default jvm options from jtreg, test.vm.opts and test.java.opts, are added.
+   * The java from the test.jdk is used to execute the command.
+   *
+   * The command line will be like:
+   * {test.jdk}/bin/java {test.vm.opts} {test.java.opts} cmds
+   *
+   * @param cmds User specifed arguments.
+   * @return The output from the process.
+   */
+  public static OutputAnalyzer executeTestJvm(String... cmds) throws Throwable {
+    ProcessBuilder pb = createJavaProcessBuilder(Utils.addTestJavaOpts(cmds));
+    return executeProcess(pb);
+  }
+
+    /**
+     * Executes a process, waits for it to finish and returns the process output.
+     * The process will have exited before this method returns.
+     * @param pb The ProcessBuilder to execute.
+     * @return The {@linkplain OutputAnalyzer} instance wrapping the process.
+     */
+    public static OutputAnalyzer executeProcess(ProcessBuilder pb) throws Exception {
+        OutputAnalyzer output = null;
+        Process p = null;
+        boolean failed = false;
+        try {
+            p = pb.start();
+            output = new OutputAnalyzer(p);
+            p.waitFor();
+
+            return output;
+        } catch (Throwable t) {
+            if (p != null) {
+                p.destroyForcibly().waitFor();
+            }
+
+            failed = true;
+            System.out.println("executeProcess() failed: " + t);
+            throw t;
+        } finally {
+            if (failed) {
+                System.err.println(getProcessLog(pb, output));
+            }
+        }
+    }
+
+  /**
+   * Executes a process, waits for it to finish and returns the process output.
+   * @param cmds The command line to execute.
+   * @return The output from the process.
+   */
+  public static OutputAnalyzer executeProcess(String... cmds) throws Throwable {
+    return executeProcess(new ProcessBuilder(cmds));
+  }
+
+  /**
+   * Used to log command line, stdout, stderr and exit code from an executed process.
+   * @param pb The executed process.
+   * @param output The output from the process.
+   */
+  public static String getProcessLog(ProcessBuilder pb, OutputAnalyzer output) {
+    String stderr = output == null ? "null" : output.getStderr();
+    String stdout = output == null ? "null" : output.getStdout();
+    String exitValue = output == null ? "null": Integer.toString(output.getExitValue());
+    StringBuilder logMsg = new StringBuilder();
+    final String nl = System.getProperty("line.separator");
+    logMsg.append("--- ProcessLog ---" + nl);
+    logMsg.append("cmd: " + getCommandLine(pb) + nl);
+    logMsg.append("exitvalue: " + exitValue + nl);
+    logMsg.append("stderr: " + stderr + nl);
+    logMsg.append("stdout: " + stdout + nl);
+    return logMsg.toString();
+  }
+
+  /**
+   * @return The full command line for the ProcessBuilder.
+   */
+  public static String getCommandLine(ProcessBuilder pb) {
+    if (pb == null) {
+      return "null";
+    }
+    StringBuilder cmd = new StringBuilder();
+    for (String s : pb.command()) {
+      cmd.append(s).append(" ");
+    }
+    return cmd.toString().trim();
+  }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/StreamPumper.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,76 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib;
+
+import java.io.OutputStream;
+import java.io.InputStream;
+import java.io.IOException;
+
+public final class StreamPumper implements Runnable {
+
+  private static final int BUF_SIZE = 256;
+
+  private final OutputStream out;
+  private final InputStream in;
+
+  /**
+   * Create a StreamPumper that reads from in and writes to out.
+   *
+   * @param in The stream to read from.
+   * @param out The stream to write to.
+   */
+  public StreamPumper(InputStream in, OutputStream out) {
+    this.in = in;
+    this.out = out;
+  }
+
+  /**
+   * Implements Thread.run(). Continuously read from <code>in</code> and write
+   * to <code>out</code> until <code>in</code> has reached end of stream. Abort
+   * on interruption. Abort on IOExceptions.
+   */
+  @Override
+  public void run() {
+    int length;
+    InputStream localIn = in;
+    OutputStream localOut = out;
+    byte[] buffer = new byte[BUF_SIZE];
+
+    try {
+      while (!Thread.interrupted() && (length = localIn.read(buffer)) > 0) {
+        localOut.write(buffer, 0, length);
+      }
+    } catch (IOException e) {
+      // Just abort if something like this happens.
+      e.printStackTrace();
+    } finally {
+      try {
+        localOut.flush();
+        in.close();
+      } catch (IOException e) {
+        e.printStackTrace();
+      }
+    }
+  }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/TimeLimitedRunner.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,86 @@
+/*
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib;
+
+import java.util.Objects;
+import java.util.concurrent.Callable;
+
+/**
+ * Auxiliary class to run target w/ given timeout.
+ */
+public class TimeLimitedRunner implements Callable<Void> {
+    private final long              stoptime;
+    private final long              timeout;
+    private final double            factor;
+    private final Callable<Boolean> target;
+
+    /**
+     * @param timeout   a timeout. zero means no time limitation
+     * @param factor    a multiplier used to estimate next iteration time
+     * @param target    a target to run
+     * @throws NullPointerException     if target is null
+     * @throws IllegalArgumentException if timeout is negative or
+                                        factor isn't positive
+     */
+    public TimeLimitedRunner(long timeout, double factor,
+            Callable<Boolean> target) {
+        Objects.requireNonNull(target, "target must not be null");
+        if (timeout < 0) {
+            throw new IllegalArgumentException("timeout[" + timeout + "] < 0");
+        }
+        if (factor <= 0d) {
+            throw new IllegalArgumentException("factor[" + factor + "] <= 0");
+        }
+        this.stoptime = System.currentTimeMillis() + timeout;
+        this.timeout = timeout;
+        this.factor = factor;
+        this.target = target;
+    }
+
+    /**
+     * Runs @{linkplan target} while it returns true and timeout isn't exceeded
+     */
+    @Override
+    public Void call() throws Exception {
+        long maxDuration = 0L;
+        long iterStart = System.currentTimeMillis();
+        if (timeout != 0 && iterStart > stoptime) {
+            return null;
+        }
+        while (target.call()) {
+            if (timeout != 0) {
+                long iterDuration = System.currentTimeMillis() - iterStart;
+                maxDuration = Math.max(maxDuration, iterDuration);
+                iterStart = System.currentTimeMillis();
+                if (iterStart + (maxDuration * factor) > stoptime) {
+                    System.out.println("Not enough time to continue execution. "
+                            + "Interrupted.");
+                    break;
+                }
+            }
+        }
+        return null;
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/Utils.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,435 @@
+/*
+ * 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
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib;
+
+import static jdk.test.lib.Asserts.assertTrue;
+import java.io.BufferedReader;
+import java.io.File;
+import java.io.FileReader;
+import java.io.IOException;
+import java.lang.reflect.Field;
+import java.net.InetAddress;
+import java.net.ServerSocket;
+import java.net.UnknownHostException;
+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.Collections;
+import java.util.List;
+import java.util.Random;
+import java.util.function.BooleanSupplier;
+import java.util.concurrent.TimeUnit;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+import java.util.stream.Collectors;
+import sun.misc.Unsafe;
+
+/**
+ * Common library for various test helper functions.
+ */
+public final class Utils {
+
+    /**
+     * Returns the sequence used by operating system to separate lines.
+     */
+    public static final String NEW_LINE = System.getProperty("line.separator");
+
+    /**
+     * Returns the value of 'test.vm.opts'system property.
+     */
+    public static final String VM_OPTIONS = System.getProperty("test.vm.opts", "").trim();
+
+    /**
+     * Returns the value of 'test.java.opts'system property.
+     */
+    public static final String JAVA_OPTIONS = System.getProperty("test.java.opts", "").trim();
+
+    private static Unsafe unsafe = null;
+
+    /**
+     * Defines property name for seed value.
+     */
+    public static final String SEED_PROPERTY_NAME = "jdk.test.lib.random.seed";
+
+    /* (non-javadoc)
+     * Random generator with (or without) predefined seed. Depends on
+     * "jdk.test.lib.random.seed" property value.
+     */
+    private static volatile Random RANDOM_GENERATOR;
+
+    /**
+     * Contains the seed value used for {@link java.util.Random} creation.
+     */
+    public static final long SEED = Long.getLong(SEED_PROPERTY_NAME, new Random().nextLong());
+    /**
+    * Returns the value of 'test.timeout.factor' system property
+    * converted to {@code double}.
+    */
+    public static final double TIMEOUT_FACTOR;
+    static {
+        String toFactor = System.getProperty("test.timeout.factor", "1.0");
+        TIMEOUT_FACTOR = Double.parseDouble(toFactor);
+    }
+
+    /**
+    * Returns the value of JTREG default test timeout in milliseconds
+    * converted to {@code long}.
+    */
+    public static final long DEFAULT_TEST_TIMEOUT = TimeUnit.SECONDS.toMillis(120);
+
+    private Utils() {
+        // Private constructor to prevent class instantiation
+    }
+
+    /**
+     * Returns the list of VM options.
+     *
+     * @return List of VM options
+     */
+    public static List<String> getVmOptions() {
+        return Arrays.asList(safeSplitString(VM_OPTIONS));
+    }
+
+    /**
+     * Returns the list of VM options with -J prefix.
+     *
+     * @return The list of VM options with -J prefix
+     */
+    public static List<String> getForwardVmOptions() {
+        String[] opts = safeSplitString(VM_OPTIONS);
+        for (int i = 0; i < opts.length; i++) {
+            opts[i] = "-J" + opts[i];
+        }
+        return Arrays.asList(opts);
+    }
+
+    /**
+     * Returns the default JTReg arguments for a jvm running a test.
+     * This is the combination of JTReg arguments test.vm.opts and test.java.opts.
+     * @return An array of options, or an empty array if no opptions.
+     */
+    public static String[] getTestJavaOpts() {
+        List<String> opts = new ArrayList<String>();
+        Collections.addAll(opts, safeSplitString(VM_OPTIONS));
+        Collections.addAll(opts, safeSplitString(JAVA_OPTIONS));
+        return opts.toArray(new String[0]);
+    }
+
+    /**
+     * Returns the default JTReg arguments for a jvm running a test without
+     * options that matches regular expressions in {@code filters}.
+     * This is the combination of JTReg arguments test.vm.opts and test.java.opts.
+     * @param filters Regular expressions used to filter out options.
+     * @return An array of options, or an empty array if no options.
+     */
+    public static String[] getFilteredTestJavaOpts(String... filters) {
+        String options[] = getTestJavaOpts();
+
+        if (filters.length == 0) {
+            return options;
+        }
+
+        List<String> filteredOptions = new ArrayList<String>(options.length);
+        Pattern patterns[] = new Pattern[filters.length];
+        for (int i = 0; i < filters.length; i++) {
+            patterns[i] = Pattern.compile(filters[i]);
+        }
+
+        for (String option : options) {
+            boolean matched = false;
+            for (int i = 0; i < patterns.length && !matched; i++) {
+                Matcher matcher = patterns[i].matcher(option);
+                matched = matcher.find();
+            }
+            if (!matched) {
+                filteredOptions.add(option);
+            }
+        }
+
+        return filteredOptions.toArray(new String[filteredOptions.size()]);
+    }
+
+    /**
+     * Combines given arguments with default JTReg arguments for a jvm running a test.
+     * This is the combination of JTReg arguments test.vm.opts and test.java.opts
+     * @return The combination of JTReg test java options and user args.
+     */
+    public static String[] addTestJavaOpts(String... userArgs) {
+        List<String> opts = new ArrayList<String>();
+        Collections.addAll(opts, getTestJavaOpts());
+        Collections.addAll(opts, userArgs);
+        return opts.toArray(new String[0]);
+    }
+
+    /**
+     * Splits a string by white space.
+     * Works like String.split(), but returns an empty array
+     * if the string is null or empty.
+     */
+    private static String[] safeSplitString(String s) {
+        if (s == null || s.trim().isEmpty()) {
+            return new String[] {};
+        }
+        return s.trim().split("\\s+");
+    }
+
+    /**
+     * @return The full command line for the ProcessBuilder.
+     */
+    public static String getCommandLine(ProcessBuilder pb) {
+        StringBuilder cmd = new StringBuilder();
+        for (String s : pb.command()) {
+            cmd.append(s).append(" ");
+        }
+        return cmd.toString();
+    }
+
+    /**
+     * Returns the free port on the local host.
+     * The function will spin until a valid port number is found.
+     *
+     * @return The port number
+     * @throws InterruptedException if any thread has interrupted the current thread
+     * @throws IOException if an I/O error occurs when opening the socket
+     */
+    public static int getFreePort() throws InterruptedException, IOException {
+        int port = -1;
+
+        while (port <= 0) {
+            Thread.sleep(100);
+
+            ServerSocket serverSocket = null;
+            try {
+                serverSocket = new ServerSocket(0);
+                port = serverSocket.getLocalPort();
+            } finally {
+                serverSocket.close();
+            }
+        }
+
+        return port;
+    }
+
+    /**
+     * Returns the name of the local host.
+     *
+     * @return The host name
+     * @throws UnknownHostException if IP address of a host could not be determined
+     */
+    public static String getHostname() throws UnknownHostException {
+        InetAddress inetAddress = InetAddress.getLocalHost();
+        String hostName = inetAddress.getHostName();
+
+        assertTrue((hostName != null && !hostName.isEmpty()),
+                "Cannot get hostname");
+
+        return hostName;
+    }
+
+    /**
+     * Uses "jcmd -l" to search for a jvm pid. This function will wait
+     * forever (until jtreg timeout) for the pid to be found.
+     * @param key Regular expression to search for
+     * @return The found pid.
+     */
+    public static int waitForJvmPid(String key) throws Throwable {
+        final long iterationSleepMillis = 250;
+        System.out.println("waitForJvmPid: Waiting for key '" + key + "'");
+        System.out.flush();
+        while (true) {
+            int pid = tryFindJvmPid(key);
+            if (pid >= 0) {
+                return pid;
+            }
+            Thread.sleep(iterationSleepMillis);
+        }
+    }
+
+    /**
+     * Searches for a jvm pid in the output from "jcmd -l".
+     *
+     * Example output from jcmd is:
+     * 12498 sun.tools.jcmd.JCmd -l
+     * 12254 /tmp/jdk8/tl/jdk/JTwork/classes/com/sun/tools/attach/Application.jar
+     *
+     * @param key A regular expression to search for.
+     * @return The found pid, or -1 if Enot found.
+     * @throws Exception If multiple matching jvms are found.
+     */
+    public static int tryFindJvmPid(String key) throws Throwable {
+        OutputAnalyzer output = null;
+        try {
+            JDKToolLauncher jcmdLauncher = JDKToolLauncher.create("jcmd");
+            jcmdLauncher.addToolArg("-l");
+            output = ProcessTools.executeProcess(jcmdLauncher.getCommand());
+            output.shouldHaveExitValue(0);
+
+            // Search for a line starting with numbers (pid), follwed by the key.
+            Pattern pattern = Pattern.compile("([0-9]+)\\s.*(" + key + ").*\\r?\\n");
+            Matcher matcher = pattern.matcher(output.getStdout());
+
+            int pid = -1;
+            if (matcher.find()) {
+                pid = Integer.parseInt(matcher.group(1));
+                System.out.println("findJvmPid.pid: " + pid);
+                if (matcher.find()) {
+                    throw new Exception("Found multiple JVM pids for key: " + key);
+                }
+            }
+            return pid;
+        } catch (Throwable t) {
+            System.out.println(String.format("Utils.findJvmPid(%s) failed: %s", key, t));
+            throw t;
+        }
+    }
+
+    /**
+     * Return the contents of the named file as a single String,
+     * or null if not found.
+     * @param filename name of the file to read
+     * @return String contents of file, or null if file not found.
+     * @throws  IOException
+     *          if an I/O error occurs reading from the file or a malformed or
+     *          unmappable byte sequence is read
+     */
+    public static String fileAsString(String filename) throws IOException {
+        Path filePath = Paths.get(filename);
+        return Files.exists(filePath)
+            ? Files.lines(filePath).collect(Collectors.joining(NEW_LINE))
+            : null;
+    }
+
+    /**
+     * @return Unsafe instance.
+     */
+    public static synchronized Unsafe getUnsafe() {
+        if (unsafe == null) {
+            try {
+                Field f = Unsafe.class.getDeclaredField("theUnsafe");
+                f.setAccessible(true);
+                unsafe = (Unsafe) f.get(null);
+            } catch (NoSuchFieldException | IllegalAccessException e) {
+                throw new RuntimeException("Unable to get Unsafe instance.", e);
+            }
+        }
+        return unsafe;
+    }
+    private static final char[] hexArray = new char[]{'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F'};
+
+    /**
+     * Returns hex view of byte array
+     *
+     * @param bytes byte array to process
+     * @return Space separated hexadecimal string representation of bytes
+     */
+
+    public static String toHexString(byte[] bytes) {
+        char[] hexView = new char[bytes.length * 3];
+        int i = 0;
+        for (byte b : bytes) {
+            hexView[i++] = hexArray[(b >> 4) & 0x0F];
+            hexView[i++] = hexArray[b & 0x0F];
+            hexView[i++] = ' ';
+        }
+        return new String(hexView);
+    }
+
+    /**
+     * Returns {@link java.util.Random} generator initialized with particular seed.
+     * The seed could be provided via system property {@link Utils#SEED_PROPERTY_NAME}
+     * In case no seed is provided, the method uses a random number.
+     * The used seed printed to stdout.
+     * @return {@link java.util.Random} generator with particular seed.
+     */
+    public static Random getRandomInstance() {
+        if (RANDOM_GENERATOR == null) {
+            synchronized (Utils.class) {
+                if (RANDOM_GENERATOR == null) {
+                    RANDOM_GENERATOR = new Random(SEED);
+                    System.out.printf("For random generator using seed: %d%n", SEED);
+                    System.out.printf("To re-run test with same seed value please add \"-D%s=%d\" to command line.%n", SEED_PROPERTY_NAME, SEED);
+                }
+            }
+        }
+        return RANDOM_GENERATOR;
+    }
+
+    /**
+     * Wait for condition to be true
+     *
+     * @param condition, a condition to wait for
+     */
+    public static final void waitForCondition(BooleanSupplier condition) {
+        waitForCondition(condition, -1L, 100L);
+    }
+
+    /**
+     * Wait until timeout for condition to be true
+     *
+     * @param condition, a condition to wait for
+     * @param timeout a time in milliseconds to wait for condition to be true
+     * specifying -1 will wait forever
+     * @return condition value, to determine if wait was successfull
+     */
+    public static final boolean waitForCondition(BooleanSupplier condition,
+            long timeout) {
+        return waitForCondition(condition, timeout, 100L);
+    }
+
+    /**
+     * Wait until timeout for condition to be true for specified time
+     *
+     * @param condition, a condition to wait for
+     * @param timeout a time in milliseconds to wait for condition to be true,
+     * specifying -1 will wait forever
+     * @param sleepTime a time to sleep value in milliseconds
+     * @return condition value, to determine if wait was successfull
+     */
+    public static final boolean waitForCondition(BooleanSupplier condition,
+            long timeout, long sleepTime) {
+        long startTime = System.currentTimeMillis();
+        while (!(condition.getAsBoolean() || (timeout != -1L
+                && ((System.currentTimeMillis() - startTime) > timeout)))) {
+            try {
+                Thread.sleep(sleepTime);
+            } catch (InterruptedException e) {
+                Thread.currentThread().interrupt();
+                throw new Error(e);
+            }
+        }
+        return condition.getAsBoolean();
+    }
+
+    /**
+     * Adjusts the provided timeout value for the TIMEOUT_FACTOR
+     * @param tOut the timeout value to be adjusted
+     * @return The timeout value adjusted for the value of "test.timeout.factor"
+     *         system property
+     */
+    public static long adjustTimeout(long tOut) {
+        return Math.round(tOut * Utils.TIMEOUT_FACTOR);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/cli/CPUSpecificCommandLineOptionTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,65 @@
+/*
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib.cli;
+
+import jdk.test.lib.cli.predicate.CPUSpecificPredicate;
+
+/**
+ * Base class for command line options tests that
+ * requires specific CPU arch or specific CPU features.
+ */
+public abstract class CPUSpecificCommandLineOptionTest
+        extends CommandLineOptionTest {
+    /**
+     * Creates new CPU specific test instance that does not
+     * require any CPU features.
+     *
+     * @param cpuArchPattern Regular expression that should
+     *                       match os.arch.
+     */
+    public CPUSpecificCommandLineOptionTest(String cpuArchPattern) {
+        this(cpuArchPattern, null, null);
+    }
+
+    /**
+     * Creates new CPU specific test instance that does not
+     * require from CPU support of {@code supportedCPUFeatures} features
+     * and no support of {@code unsupportedCPUFeatures}.
+     *
+     * @param cpuArchPattern Regular expression that should
+     *                       match os.arch.
+     * @param supportedCPUFeatures Array with names of features that
+     *                             should be supported by CPU. If {@code null},
+     *                             then no features have to be supported.
+     * @param unsupportedCPUFeatures Array with names of features that
+     *                               should not be supported by CPU.
+     *                               If {@code null}, then CPU may support any
+     *                               features.
+     */
+    public CPUSpecificCommandLineOptionTest(String cpuArchPattern,
+            String supportedCPUFeatures[], String unsupportedCPUFeatures[]) {
+        super(new CPUSpecificPredicate(cpuArchPattern, supportedCPUFeatures,
+                unsupportedCPUFeatures));
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/cli/CommandLineOptionTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,396 @@
+/*
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib.cli;
+
+import java.util.List;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.function.BooleanSupplier;
+
+import jdk.test.lib.*;
+
+/**
+ * Base class for command line option tests.
+ */
+public abstract class CommandLineOptionTest {
+    public static final String UNLOCK_DIAGNOSTIC_VM_OPTIONS
+            = "-XX:+UnlockDiagnosticVMOptions";
+    public static final String UNLOCK_EXPERIMENTAL_VM_OPTIONS
+            = "-XX:+UnlockExperimentalVMOptions";
+    protected static final String UNRECOGNIZED_OPTION_ERROR_FORMAT
+            = "Unrecognized VM option '[+-]?%s(=.*)?'";
+    protected static final String EXPERIMENTAL_OPTION_ERROR_FORMAT
+            = "VM option '%s' is experimental and must be enabled via "
+            + "-XX:\\+UnlockExperimentalVMOptions.";
+    protected static final String DIAGNOSTIC_OPTION_ERROR_FORMAT
+            = " VM option '%s' is diagnostic and must be enabled via "
+            + "-XX:\\+UnlockDiagnosticVMOptions.";
+    private static final String PRINT_FLAGS_FINAL_FORMAT = "%s\\s*:?=\\s*%s";
+
+    /**
+     * Verifies that JVM startup behavior matches our expectations.
+     *
+     * @param option an option that should be passed to JVM
+     * @param expectedMessages an array of patterns that should occur
+     *                          in JVM output. If {@code null} then
+     *                          JVM output could be empty.
+     * @param unexpectedMessages an array of patterns that should not
+     *                           occur in JVM output. If {@code null} then
+     *                           JVM output could be empty.
+     * @param exitErrorMessage message that will be shown if exit code is not
+     *                           as expected.
+     * @param wrongWarningMessage message that will be shown if warning
+     *                           messages are not as expected.
+     * @param exitCode expected exit code.
+     * @throws Throwable if verification fails or some other issues occur.
+     */
+    public static void verifyJVMStartup(String option,
+            String expectedMessages[], String unexpectedMessages[],
+            String exitErrorMessage, String wrongWarningMessage,
+            ExitCode exitCode) throws Throwable {
+        CommandLineOptionTest.verifyJVMStartup(expectedMessages,
+                unexpectedMessages, exitErrorMessage,
+                wrongWarningMessage, exitCode, false, option);
+    }
+
+    /**
+     * Verifies that JVM startup behavior matches our expectations.
+     *
+     * @param expectedMessages an array of patterns that should occur
+     *                         in JVM output. If {@code null} then
+     *                         JVM output could be empty.
+     * @param unexpectedMessages an array of patterns that should not
+     *                           occur in JVM output. If {@code null} then
+     *                           JVM output could be empty.
+     * @param exitErrorMessage message that will be shown if exit code is not
+     *                           as expected.
+     * @param wrongWarningMessage message that will be shown if warning
+     *                           messages are not as expected.
+     * @param exitCode expected exit code.
+     * @param addTestVMOptions if {@code true} then test VM options will be
+     *                         passed to VM.
+     * @param options options that should be passed to VM in addition to mode
+     *                flag.
+     * @throws Throwable if verification fails or some other issues occur.
+     */
+    public static void verifyJVMStartup(String expectedMessages[],
+            String unexpectedMessages[], String exitErrorMessage,
+            String wrongWarningMessage, ExitCode exitCode,
+            boolean addTestVMOptions, String... options)
+                    throws Throwable {
+        List<String> finalOptions = new ArrayList<>();
+        if (addTestVMOptions) {
+            Collections.addAll(finalOptions, Utils.getTestJavaOpts());
+        }
+        Collections.addAll(finalOptions, options);
+        finalOptions.add("-version");
+
+        ProcessBuilder processBuilder
+                = ProcessTools.createJavaProcessBuilder(finalOptions.toArray(
+                new String[finalOptions.size()]));
+        OutputAnalyzer outputAnalyzer
+                = new OutputAnalyzer(processBuilder.start());
+
+        try {
+                outputAnalyzer.shouldHaveExitValue(exitCode.value);
+        } catch (RuntimeException e) {
+            String errorMessage = String.format(
+                    "JVM process should have exit value '%d'.%n%s",
+                    exitCode.value, exitErrorMessage);
+            throw new AssertionError(errorMessage, e);
+        }
+
+
+        if (expectedMessages != null) {
+            for (String expectedMessage : expectedMessages) {
+                try {
+                    outputAnalyzer.shouldMatch(expectedMessage);
+                } catch (RuntimeException e) {
+                    String errorMessage = String.format(
+                            "Expected message not found: '%s'.%n%s",
+                            expectedMessage, wrongWarningMessage);
+                    throw new AssertionError(errorMessage, e);
+                }
+            }
+        }
+
+        if (unexpectedMessages != null) {
+            for (String unexpectedMessage : unexpectedMessages) {
+                try {
+                    outputAnalyzer.shouldNotMatch(unexpectedMessage);
+                } catch (RuntimeException e) {
+                    String errorMessage = String.format(
+                            "Unexpected message found: '%s'.%n%s",
+                            unexpectedMessage, wrongWarningMessage);
+                    throw new AssertionError(errorMessage, e);
+                }
+            }
+        }
+    }
+
+    /**
+     * Verifies that JVM startup behavior matches our expectations when type
+     * of newly started VM is the same as the type of current.
+     *
+     * @param expectedMessages an array of patterns that should occur
+     *                         in JVM output. If {@code null} then
+     *                         JVM output could be empty.
+     * @param unexpectedMessages an array of patterns that should not
+     *                           occur in JVM output. If {@code null} then
+     *                           JVM output could be empty.
+     * @param exitErrorMessage Message that will be shown if exit value is not
+     *                           as expected.
+     * @param wrongWarningMessage message that will be shown if warning
+     *                           messages are not as expected.
+     * @param exitCode expected exit code.
+     * @param options options that should be passed to VM in addition to mode
+     *                flag.
+     * @throws Throwable if verification fails or some other issues occur.
+     */
+    public static void verifySameJVMStartup(String expectedMessages[],
+            String unexpectedMessages[], String exitErrorMessage,
+            String wrongWarningMessage, ExitCode exitCode, String... options)
+            throws Throwable {
+        List<String> finalOptions = new ArrayList<>();
+        finalOptions.add(CommandLineOptionTest.getVMTypeOption());
+        Collections.addAll(finalOptions, options);
+
+        CommandLineOptionTest.verifyJVMStartup(expectedMessages,
+                unexpectedMessages, exitErrorMessage,
+                wrongWarningMessage, exitCode, false,
+                finalOptions.toArray(new String[finalOptions.size()]));
+    }
+
+    /**
+     * Verifies that value of specified JVM option is the same as
+     * expected value.
+     * This method filter out option with {@code optionName}
+     * name from test java options.
+     *
+     * @param optionName a name of tested option.
+     * @param expectedValue expected value of tested option.
+     * @param optionErrorString message will be shown if option value is not as
+     *                         expected.
+     * @param additionalVMOpts additional options that should be
+     *                         passed to JVM.
+     * @throws Throwable if verification fails or some other issues occur.
+     */
+    public static void verifyOptionValue(String optionName,
+            String expectedValue, String optionErrorString,
+            String... additionalVMOpts) throws Throwable {
+        verifyOptionValue(optionName, expectedValue,  optionErrorString,
+                true, additionalVMOpts);
+    }
+
+    /**
+     * Verifies that value of specified JVM option is the same as
+     * expected value.
+     * This method filter out option with {@code optionName}
+     * name from test java options.
+     *
+     * @param optionName a name of tested option.
+     * @param expectedValue expected value of tested option.
+     * @param addTestVmOptions if {@code true}, then test VM options
+     *                         will be used.
+     * @param optionErrorString message will be shown if option value is not as
+     *                         expected.
+     * @param additionalVMOpts additional options that should be
+     *                         passed to JVM.
+     * @throws Throwable if verification fails or some other issues
+     *                          occur.
+     */
+    public static void verifyOptionValue(String optionName,
+            String expectedValue, String optionErrorString,
+            boolean addTestVmOptions, String... additionalVMOpts)
+                    throws Throwable {
+        List<String> vmOpts = new ArrayList<>();
+
+        if (addTestVmOptions) {
+            Collections.addAll(vmOpts,
+                               Utils.getFilteredTestJavaOpts(optionName));
+        }
+        Collections.addAll(vmOpts, additionalVMOpts);
+        Collections.addAll(vmOpts, "-XX:+PrintFlagsFinal", "-version");
+
+        ProcessBuilder processBuilder = ProcessTools.createJavaProcessBuilder(
+                vmOpts.toArray(new String[vmOpts.size()]));
+
+        OutputAnalyzer outputAnalyzer
+                = new OutputAnalyzer(processBuilder.start());
+
+        try {
+            outputAnalyzer.shouldHaveExitValue(0);
+        } catch (RuntimeException e) {
+            String errorMessage = String.format(
+                    "JVM should start with option '%s' without errors.",
+                    optionName);
+            throw new AssertionError(errorMessage, e);
+        }
+        try {
+        outputAnalyzer.shouldMatch(String.format(
+                CommandLineOptionTest.PRINT_FLAGS_FINAL_FORMAT,
+                optionName, expectedValue));
+        } catch (RuntimeException e) {
+            String errorMessage =  String.format(
+                    "Option '%s' is expected to have '%s' value%n%s",
+                    optionName, expectedValue,
+                    optionErrorString);
+            throw new AssertionError(errorMessage, e);
+        }
+    }
+
+    /**
+     * Verifies that value of specified JVM when type of newly started VM
+     * is the same as the type of current.
+     * This method filter out option with {@code optionName}
+     * name from test java options.
+     * Only mode flag will be passed to VM in addition to
+     * {@code additionalVMOpts}
+     *
+     * @param optionName name of tested option.
+     * @param expectedValue expected value of tested option.
+     * @param optionErrorString message to show if option has another value
+     * @param additionalVMOpts additional options that should be
+     *                         passed to JVM.
+     * @throws Throwable if verification fails or some other issues occur.
+     */
+    public static void verifyOptionValueForSameVM(String optionName,
+            String expectedValue, String optionErrorString,
+            String... additionalVMOpts) throws Throwable {
+        List<String> finalOptions = new ArrayList<>();
+        finalOptions.add(CommandLineOptionTest.getVMTypeOption());
+        Collections.addAll(finalOptions, additionalVMOpts);
+
+        CommandLineOptionTest.verifyOptionValue(optionName, expectedValue,
+                optionErrorString, false,
+                finalOptions.toArray(new String[finalOptions.size()]));
+    }
+
+    /**
+     * Prepares boolean command line flag with name {@code name} according
+     * to it's {@code value}.
+     *
+     * @param name the name of option to be prepared
+     * @param value the value of option
+     * @return prepared command line flag
+     */
+    public static String prepareBooleanFlag(String name, boolean value) {
+        return String.format("-XX:%c%s", (value ? '+' : '-'), name);
+    }
+
+    /**
+     * Prepares numeric command line flag with name {@code name} by setting
+     * it's value to {@code value}.
+     *
+     * @param name the name of option to be prepared
+     * @param value the value of option
+     * @return prepared command line flag
+     */
+    public static String prepareNumericFlag(String name, Number value) {
+        return String.format("-XX:%s=%s", name, value.toString());
+    }
+
+    /**
+     * Returns message that should occur in VM output if option
+     * {@code optionName} if unrecognized.
+     *
+     * @param optionName the name of option for which message should be returned
+     * @return message saying that option {@code optionName} is unrecognized
+     */
+    public static String getUnrecognizedOptionErrorMessage(String optionName) {
+        return String.format(
+                CommandLineOptionTest.UNRECOGNIZED_OPTION_ERROR_FORMAT,
+                optionName);
+    }
+
+    /**
+     * Returns message that should occur in VM output if option
+     * {@code optionName} is experimental and
+     * -XX:+UnlockExperimentalVMOptions was not passed to VM.
+     *
+     * @param optionName the name of option for which message should be returned
+     * @return message saying that option {@code optionName} is experimental
+     */
+    public static String getExperimentalOptionErrorMessage(String optionName) {
+        return String.format(
+                CommandLineOptionTest.EXPERIMENTAL_OPTION_ERROR_FORMAT,
+                optionName);
+    }
+
+    /**
+     * Returns message that should occur in VM output if option
+     * {@code optionName} is diagnostic and -XX:+UnlockDiagnosticVMOptions
+     * was not passed to VM.
+     *
+     * @param optionName the name of option for which message should be returned
+     * @return message saying that option {@code optionName} is diganostic
+     */
+    public static String getDiagnosticOptionErrorMessage(String optionName) {
+        return String.format(
+                CommandLineOptionTest.DIAGNOSTIC_OPTION_ERROR_FORMAT,
+                optionName);
+    }
+
+    /**
+     * @return option required to start a new VM with the same type as current.
+     * @throws RuntimeException when VM type is unknown.
+     */
+    private static String getVMTypeOption() {
+        if (Platform.isServer()) {
+            return "-server";
+        } else if (Platform.isClient()) {
+            return "-client";
+        } else if (Platform.isMinimal()) {
+            return "-minimal";
+        } else if (Platform.isGraal()) {
+            return "-graal";
+        }
+        throw new RuntimeException("Unknown VM mode.");
+    }
+
+    private final BooleanSupplier predicate;
+
+    /**
+     * Constructs new CommandLineOptionTest that will be executed only if
+     * predicate {@code predicate} return {@code true}.
+     * @param predicate a predicate responsible for test's preconditions check.
+     */
+    public CommandLineOptionTest(BooleanSupplier predicate) {
+        this.predicate = predicate;
+    }
+
+    /**
+     * Runs command line option test.
+     */
+    public final void test() throws Throwable {
+        if (predicate.getAsBoolean()) {
+            runTestCases();
+        }
+    }
+
+    /**
+     * @throws Throwable if some issue happened during test cases execution.
+     */
+    protected abstract void runTestCases() throws Throwable;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/cli/predicate/AndPredicate.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,41 @@
+/*
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib.cli.predicate;
+
+import java.util.function.BooleanSupplier;
+
+public class AndPredicate implements BooleanSupplier {
+    private final BooleanSupplier a;
+    private final BooleanSupplier b;
+
+    public AndPredicate(BooleanSupplier a, BooleanSupplier b) {
+        this.a = a;
+        this.b = b;
+    }
+
+    @Override
+    public boolean getAsBoolean() {
+        return a.getAsBoolean() && b.getAsBoolean();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/cli/predicate/CPUSpecificPredicate.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,71 @@
+/*
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package jdk.test.lib.cli.predicate;
+
+import jdk.test.lib.Platform;
+import sun.hotspot.cpuinfo.CPUInfo;
+
+import java.util.function.BooleanSupplier;
+
+public class CPUSpecificPredicate implements BooleanSupplier {
+    private final String cpuArchPattern;
+    private final String supportedCPUFeatures[];
+    private final String unsupportedCPUFeatures[];
+
+    public CPUSpecificPredicate(String cpuArchPattern,
+            String supportedCPUFeatures[],
+            String unsupportedCPUFeatures[]) {
+        this.cpuArchPattern = cpuArchPattern;
+        this.supportedCPUFeatures = supportedCPUFeatures;
+        this.unsupportedCPUFeatures = unsupportedCPUFeatures;
+    }
+
+    @Override
+    public boolean getAsBoolean() {
+        if (!Platform.getOsArch().matches(cpuArchPattern)) {
+            System.out.println("CPU arch does not match " + cpuArchPattern);
+            return false;
+        }
+
+        if (supportedCPUFeatures != null) {
+            for (String feature : supportedCPUFeatures) {
+                if (!CPUInfo.hasFeature(feature)) {
+                    System.out.println("CPU does not support " + feature
+                            + " feature");
+                    return false;
+                }
+            }
+        }
+
+        if (unsupportedCPUFeatures != null) {
+            for (String feature : unsupportedCPUFeatures) {
+                if (CPUInfo.hasFeature(feature)) {
+                    System.out.println("CPU support " + feature + " feature");
+                    return false;
+                }
+            }
+        }
+        return true;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/cli/predicate/NotPredicate.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,40 @@
+/*
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+
+package jdk.test.lib.cli.predicate;
+
+import java.util.function.BooleanSupplier;
+
+public class NotPredicate implements BooleanSupplier {
+    private final BooleanSupplier s;
+
+    public NotPredicate(BooleanSupplier s) {
+        this.s = s;
+    }
+
+    @Override
+    public boolean getAsBoolean() {
+        return !s.getAsBoolean();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/cli/predicate/OrPredicate.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,42 @@
+/*
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+
+package jdk.test.lib.cli.predicate;
+
+import java.util.function.BooleanSupplier;
+
+public class OrPredicate implements BooleanSupplier {
+    private final BooleanSupplier a;
+    private final BooleanSupplier b;
+
+    public OrPredicate(BooleanSupplier a, BooleanSupplier b) {
+        this.a = a;
+        this.b = b;
+    }
+
+    @Override
+    public boolean getAsBoolean() {
+        return a.getAsBoolean() || b.getAsBoolean();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/dcmd/CommandExecutor.java	Wed Jul 05 20:35:10 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.
+ */
+
+package jdk.test.lib.dcmd;
+
+import jdk.test.lib.OutputAnalyzer;
+
+/**
+ * Abstract base class for Diagnostic Command executors
+ */
+public abstract class CommandExecutor {
+
+    /**
+     * Execute a diagnostic command
+     *
+     * @param cmd The diagnostic command to execute
+     * @return an {@link jdk.testlibrary.OutputAnalyzer} encapsulating the output of the command
+     * @throws CommandExecutorException if there is an exception on the "calling side" while trying to execute the
+     *          Diagnostic Command. Exceptions thrown on the remote side are available as textual representations in
+     *          stderr, regardless of the specific executor used.
+     */
+    public final OutputAnalyzer execute(String cmd) throws CommandExecutorException {
+        return execute(cmd, false);
+    }
+
+    /**
+     * Execute a diagnostic command
+     *
+     * @param cmd The diagnostic command to execute
+     * @param silent Do not print the command output
+     * @return an {@link jdk.testlibrary.OutputAnalyzer} encapsulating the output of the command
+     * @throws CommandExecutorException if there is an exception on the "calling side" while trying to execute the
+     *          Diagnostic Command. Exceptions thrown on the remote side are available as textual representations in
+     *          stderr, regardless of the specific executor used.
+     */
+    public final OutputAnalyzer execute(String cmd, boolean silent) throws CommandExecutorException {
+        if (!silent) {
+            System.out.printf("Running DCMD '%s' through '%s'%n", cmd, this.getClass().getSimpleName());
+        }
+
+        OutputAnalyzer oa = executeImpl(cmd);
+
+        if (!silent) {
+            System.out.println("---------------- stdout ----------------");
+            System.out.println(oa.getStdout());
+            System.out.println("---------------- stderr ----------------");
+            System.out.println(oa.getStderr());
+            System.out.println("----------------------------------------");
+            System.out.println();
+        }
+        return oa;
+    }
+
+    protected abstract OutputAnalyzer executeImpl(String cmd) throws CommandExecutorException;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/dcmd/CommandExecutorException.java	Wed Jul 05 20:35:10 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 jdk.test.lib.dcmd;
+
+/**
+ * CommandExecutorException encapsulates exceptions thrown (on the "calling side") from the execution of Diagnostic
+ * Commands
+ */
+public class CommandExecutorException extends RuntimeException {
+    private static final long serialVersionUID = -7039597746579144280L;
+
+    public CommandExecutorException(String message, Throwable e) {
+        super(message, e);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/dcmd/FileJcmdExecutor.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,81 @@
+/*
+ * 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 jdk.test.lib.dcmd;
+
+import java.io.File;
+import java.io.IOException;
+import java.io.PrintWriter;
+import java.util.Arrays;
+import java.util.List;
+
+/**
+ * Executes Diagnostic Commands on the target VM (specified by pid) using the jcmd tool and its ability to read
+ *          Diagnostic Commands from a file.
+ */
+public class FileJcmdExecutor extends PidJcmdExecutor {
+
+    /**
+     * Instantiates a new FileJcmdExecutor targeting the current VM
+     */
+    public FileJcmdExecutor() {
+        super();
+    }
+
+    /**
+     * Instantiates a new FileJcmdExecutor targeting the VM indicated by the given pid
+     *
+     * @param target Pid of the target VM
+     */
+    public FileJcmdExecutor(String target) {
+        super(target);
+    }
+
+    protected List<String> createCommandLine(String cmd) throws CommandExecutorException {
+        File cmdFile = createTempFile();
+        writeCommandToTemporaryFile(cmd, cmdFile);
+
+        return Arrays.asList(jcmdBinary, Integer.toString(pid),
+                "-f", cmdFile.getAbsolutePath());
+    }
+
+    private void writeCommandToTemporaryFile(String cmd, File cmdFile) {
+        try (PrintWriter pw = new PrintWriter(cmdFile)) {
+            pw.println(cmd);
+        } catch (IOException e) {
+            String message = "Could not write to file: " + cmdFile.getAbsolutePath();
+            throw new CommandExecutorException(message, e);
+        }
+    }
+
+    private File createTempFile() {
+        try {
+            File cmdFile = File.createTempFile("input", "jcmd");
+            cmdFile.deleteOnExit();
+            return cmdFile;
+        } catch (IOException e) {
+            throw new CommandExecutorException("Could not create temporary file", e);
+        }
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/dcmd/JMXExecutor.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,187 @@
+/*
+ * 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 jdk.test.lib.dcmd;
+
+import jdk.test.lib.OutputAnalyzer;
+
+import javax.management.*;
+import javax.management.remote.JMXConnector;
+import javax.management.remote.JMXConnectorFactory;
+import javax.management.remote.JMXServiceURL;
+
+import java.io.IOException;
+import java.io.PrintWriter;
+import java.io.StringWriter;
+
+import java.lang.management.ManagementFactory;
+
+import java.util.HashMap;
+
+/**
+ * Executes Diagnostic Commands on the target VM (specified by a host/port combination or a full JMX Service URL) using
+ * the JMX interface. If the target is not the current VM, the JMX Remote interface must be enabled beforehand.
+ */
+public class JMXExecutor extends CommandExecutor {
+
+    private final MBeanServerConnection mbs;
+
+    /**
+     * Instantiates a new JMXExecutor targeting the current VM
+     */
+    public JMXExecutor() {
+        super();
+        mbs = ManagementFactory.getPlatformMBeanServer();
+    }
+
+    /**
+     * Instantiates a new JMXExecutor targeting the VM indicated by the given host/port combination or a full JMX
+     * Service URL
+     *
+     * @param target a host/port combination on the format "host:port" or a full JMX Service URL of the target VM
+     */
+    public JMXExecutor(String target) {
+        String urlStr;
+
+        if (target.matches("^\\w[\\w\\-]*(\\.[\\w\\-]+)*:\\d+$")) {
+            /* Matches "hostname:port" */
+            urlStr = String.format("service:jmx:rmi:///jndi/rmi://%s/jmxrmi", target);
+        } else if (target.startsWith("service:")) {
+            urlStr = target;
+        } else {
+            throw new IllegalArgumentException("Could not recognize target string: " + target);
+        }
+
+        try {
+            JMXServiceURL url = new JMXServiceURL(urlStr);
+            JMXConnector c = JMXConnectorFactory.connect(url, new HashMap<>());
+            mbs = c.getMBeanServerConnection();
+        } catch (IOException e) {
+            throw new CommandExecutorException("Could not initiate connection to target: " + target, e);
+        }
+    }
+
+    protected OutputAnalyzer executeImpl(String cmd) throws CommandExecutorException {
+        String stdout = "";
+        String stderr = "";
+
+        String[] cmdParts = cmd.split(" ", 2);
+        String operation = commandToMethodName(cmdParts[0]);
+        Object[] dcmdArgs = produceArguments(cmdParts);
+        String[] signature = {String[].class.getName()};
+
+        ObjectName beanName = getMBeanName();
+
+        try {
+            stdout = (String) mbs.invoke(beanName, operation, dcmdArgs, signature);
+        }
+
+        /* Failures on the "local" side, the one invoking the command. */
+        catch (ReflectionException e) {
+            Throwable cause = e.getCause();
+            if (cause instanceof NoSuchMethodException) {
+                /* We want JMXExecutor to match the behavior of the other CommandExecutors */
+                String message = "Unknown diagnostic command: " + operation;
+                stderr = exceptionTraceAsString(new IllegalArgumentException(message, e));
+            } else {
+                rethrowExecutorException(operation, dcmdArgs, e);
+            }
+        }
+
+        /* Failures on the "local" side, the one invoking the command. */
+        catch (InstanceNotFoundException | IOException e) {
+            rethrowExecutorException(operation, dcmdArgs, e);
+        }
+
+        /* Failures on the remote side, the one executing the invoked command. */
+        catch (MBeanException e) {
+            stdout = exceptionTraceAsString(e);
+        }
+
+        return new OutputAnalyzer(stdout, stderr);
+    }
+
+    private void rethrowExecutorException(String operation, Object[] dcmdArgs,
+                                          Exception e) throws CommandExecutorException {
+        String message = String.format("Could not invoke: %s %s", operation,
+                String.join(" ", (String[]) dcmdArgs[0]));
+        throw new CommandExecutorException(message, e);
+    }
+
+    private ObjectName getMBeanName() throws CommandExecutorException {
+        String MBeanName = "com.sun.management:type=DiagnosticCommand";
+
+        try {
+            return new ObjectName(MBeanName);
+        } catch (MalformedObjectNameException e) {
+            String message = "MBean not found: " + MBeanName;
+            throw new CommandExecutorException(message, e);
+        }
+    }
+
+    private Object[] produceArguments(String[] cmdParts) {
+        Object[] dcmdArgs = {new String[0]}; /* Default: No arguments */
+
+        if (cmdParts.length == 2) {
+            dcmdArgs[0] = cmdParts[1].split(" ");
+        }
+        return dcmdArgs;
+    }
+
+    /**
+     * Convert from diagnostic command to MBean method name
+     *
+     * Examples:
+     * help            --> help
+     * VM.version      --> vmVersion
+     * VM.command_line --> vmCommandLine
+     */
+    private static String commandToMethodName(String cmd) {
+        String operation = "";
+        boolean up = false; /* First letter is to be lower case */
+
+        /*
+         * If a '.' or '_' is encountered it is not copied,
+         * instead the next character will be converted to upper case
+         */
+        for (char c : cmd.toCharArray()) {
+            if (('.' == c) || ('_' == c)) {
+                up = true;
+            } else if (up) {
+                operation = operation.concat(Character.toString(c).toUpperCase());
+                up = false;
+            } else {
+                operation = operation.concat(Character.toString(c).toLowerCase());
+            }
+        }
+
+        return operation;
+    }
+
+    private static String exceptionTraceAsString(Throwable cause) {
+        StringWriter sw = new StringWriter();
+        cause.printStackTrace(new PrintWriter(sw));
+        return sw.toString();
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/dcmd/JcmdExecutor.java	Wed Jul 05 20:35:10 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.
+ */
+
+package jdk.test.lib.dcmd;
+
+import jdk.test.lib.JDKToolFinder;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
+
+import java.util.List;
+
+/**
+ * Base class for Diagnostic Command Executors using the jcmd tool
+ */
+public abstract class JcmdExecutor extends CommandExecutor {
+    protected String jcmdBinary;
+
+    protected abstract List<String> createCommandLine(String cmd) throws CommandExecutorException;
+
+    protected JcmdExecutor() {
+        jcmdBinary = JDKToolFinder.getJDKTool("jcmd");
+    }
+
+    protected OutputAnalyzer executeImpl(String cmd) throws CommandExecutorException {
+        List<String> commandLine = createCommandLine(cmd);
+
+        try {
+            System.out.printf("Executing command '%s'%n", commandLine);
+            OutputAnalyzer output = ProcessTools.executeProcess(new ProcessBuilder(commandLine));
+            System.out.printf("Command returned with exit code %d%n", output.getExitValue());
+
+            return output;
+        } catch (Exception e) {
+            String message = String.format("Caught exception while executing '%s'", commandLine);
+            throw new CommandExecutorException(message, e);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/dcmd/MainClassJcmdExecutor.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,57 @@
+/*
+ * 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 jdk.test.lib.dcmd;
+
+import java.util.Arrays;
+import java.util.List;
+
+/**
+ * Executes Diagnostic Commands on the target VM (specified by main class) using the jcmd tool
+ */
+public class MainClassJcmdExecutor extends JcmdExecutor {
+    private final String mainClass;
+
+    /**
+     * Instantiates a new MainClassJcmdExecutor targeting the current VM
+     */
+    public MainClassJcmdExecutor() {
+        super();
+        mainClass = System.getProperty("sun.java.command").split(" ")[0];
+    }
+
+    /**
+     * Instantiates a new MainClassJcmdExecutor targeting the VM indicated by the given main class
+     *
+     * @param target Main class of the target VM
+     */
+    public MainClassJcmdExecutor(String target) {
+        super();
+        mainClass = target;
+    }
+
+    protected List<String> createCommandLine(String cmd) throws CommandExecutorException {
+        return Arrays.asList(jcmdBinary, mainClass, cmd);
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/dcmd/PidJcmdExecutor.java	Wed Jul 05 20:35:10 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.
+ */
+
+package jdk.test.lib.dcmd;
+
+import jdk.test.lib.ProcessTools;
+
+import java.util.Arrays;
+import java.util.List;
+
+/**
+ * Executes Diagnostic Commands on the target VM (specified by pid) using the jcmd tool
+ */
+public class PidJcmdExecutor extends JcmdExecutor {
+    protected final int pid;
+
+    /**
+     * Instantiates a new PidJcmdExecutor targeting the current VM
+     */
+    public PidJcmdExecutor() {
+        super();
+        try {
+            pid = ProcessTools.getProcessId();
+        } catch (Exception e) {
+            throw new CommandExecutorException("Could not determine own pid", e);
+        }
+    }
+
+    /**
+     * Instantiates a new PidJcmdExecutor targeting the VM indicated by the given pid
+     *
+     * @param target Pid of the target VM
+     */
+    public PidJcmdExecutor(String target) {
+        super();
+        pid = Integer.valueOf(target);
+    }
+
+    protected List<String> createCommandLine(String cmd) throws CommandExecutorException {
+        return Arrays.asList(jcmdBinary, Integer.toString(pid), cmd);
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/dtrace/DtraceResultsAnalyzer.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,29 @@
+/*
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.test.lib.dtrace;
+
+import jdk.test.lib.OutputAnalyzer;
+
+public interface DtraceResultsAnalyzer {
+    public void analyze(OutputAnalyzer oa, String logFilePath);
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/hotspot/test/testlibrary/jdk/test/lib/dtrace/DtraceRunner.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,121 @@
+/*
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+package jdk.test.lib.dtrace;
+
+import jdk.test.lib.Asserts;
+import jdk.test.lib.OutputAnalyzer;
+import java.io.File;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.List;
+
+public class DtraceRunner {
+
+    private static final String DTRACE_DEFAULT_PATH = "/usr/sbin/dtrace";
+    private static final String DTRACE_PATH_PROPERTY
+            = "com.oracle.test.dtrace.path";
+    private static final String OUTPUT_FILE_DTRACE_OPTION = "o";
+    private static final String RUN_COMMAND_DTRACE_OPTION = "c";
+    private static final String RUN_SCRIPT_DTRACE_OPTION = "s";
+    private static final String ALLOW_ZERO_PROBE_DESCRIPTION_DTRACE_OPTION = "Z";
+    private static final String DTRACE_OPTION_PREFIX = "-";
+    public static final String PERMIT_DESTRUCTIVE_ACTIONS_DTRACE_OPTION = "w";
+    public static final String DTRACE_OUT_LOG = "dtrace.out";
+
+    private final String dtraceExecutable;
+
+    public DtraceRunner() {
+        dtraceExecutable = getDtracePath();
+    }
+
+    private List<String> getLaunchCmd(String java, String javaOpts,
+            String execClass, String testArgs, String dtraceScript,
+            String dtraceAddOpts) {
+        Asserts.assertTrue(!java.matches("\\s"), "Current dtrace implementation"
+                + " can't handle whitespaces in application path");
+        List<String> result = new ArrayList<>();
+        result.add(dtraceExecutable);
+        result.add(DTRACE_OPTION_PREFIX + System.getProperty("sun.arch.data.model"));
+        result.add(DTRACE_OPTION_PREFIX
+                + ALLOW_ZERO_PROBE_DESCRIPTION_DTRACE_OPTION
+                + ((dtraceAddOpts == null) ? "" : dtraceAddOpts)
+                + RUN_SCRIPT_DTRACE_OPTION); // run_script should be last one
+        result.add(dtraceScript);
+        result.add(DTRACE_OPTION_PREFIX + OUTPUT_FILE_DTRACE_OPTION);
+        result.add(DTRACE_OUT_LOG);
+        result.add(DTRACE_OPTION_PREFIX + RUN_COMMAND_DTRACE_OPTION);
+        result.add(java + " " + javaOpts + " " + execClass + " " + testArgs);
+        return result;
+    }
+
+    private void backupLogFile(File file) {
+        if (file.exists()) {
+            file.renameTo(new File(file.getPath() + ".bak"));
+        }
+    }
+
+    public void runDtrace(String java, String javaOpts, String execClass,
+            String testArgs, String dtraceScript, String dtraceAddOpts,
+            DtraceResultsAnalyzer analyzer) {
+        backupLogFile(new File(DTRACE_OUT_LOG));
+        ProcessBuilder pbuilder = new ProcessBuilder(
+                getLaunchCmd(java, javaOpts, execClass, testArgs,
+                        dtraceScript, dtraceAddOpts));
+        OutputAnalyzer oa;
+        try {
+            oa = new OutputAnalyzer(pbuilder.start());
+        } catch (IOException e) {
+            throw new Error("TESTBUG: Can't start process", e);
+        }
+        analyzer.analyze(oa, DTRACE_OUT_LOG);
+    }
+
+    public static boolean dtraceAvailable() {
+        String path = getDtracePath();
+        if (path == null) {
+            return false;
+        }
+        // now we'll launch dtrace to trace itself just to be sure it works
+        // and have all additional previleges set
+        ProcessBuilder pbuilder = new ProcessBuilder(path, path);
+        try {
+            OutputAnalyzer oa = new OutputAnalyzer(pbuilder.start());
+            if (oa.getExitValue() != 0) {
+                return false;
+            }
+        } catch (IOException e) {
+            throw new Error("Couldn't launch dtrace", e);
+        }
+        return true;
+    }
+
+    private static String getDtracePath() {
+        String propPath = System.getProperty(DTRACE_PATH_PROPERTY);
+        if (propPath != null && new File(propPath).exists()) {
+            return propPath;
+        } else if (new File(DTRACE_DEFAULT_PATH).exists()) {
+            return DTRACE_DEFAULT_PATH;
+        }
+        return null;
+    }
+}
--- a/hotspot/test/testlibrary_tests/AssertsTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/testlibrary_tests/AssertsTest.java	Wed Jul 05 20:35:10 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
@@ -21,7 +21,7 @@
  * questions.
  */
 
-import static com.oracle.java.testlibrary.Asserts.*;
+import static jdk.test.lib.Asserts.*;
 
 /* @test
  * @summary Tests the different assertions in the Assert class
--- a/hotspot/test/testlibrary_tests/OutputAnalyzerReportingTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/testlibrary_tests/OutputAnalyzerReportingTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -35,8 +35,8 @@
 import java.io.ByteArrayOutputStream;
 import java.io.PrintStream;
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
-import com.oracle.java.testlibrary.ProcessTools;
+import jdk.test.lib.OutputAnalyzer;
+import jdk.test.lib.ProcessTools;
 
 
 public class OutputAnalyzerReportingTest {
--- a/hotspot/test/testlibrary_tests/OutputAnalyzerTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/testlibrary_tests/OutputAnalyzerTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,7 +29,7 @@
  *          java.management
  */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
+import jdk.test.lib.OutputAnalyzer;
 
 public class OutputAnalyzerTest {
 
--- a/hotspot/test/testlibrary_tests/RandomGeneratorTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/testlibrary_tests/RandomGeneratorTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,14 +32,14 @@
  * @run driver RandomGeneratorTest DIFFERENT_SEED
  */
 
-import com.oracle.java.testlibrary.ProcessTools;
-import com.oracle.java.testlibrary.Utils;
+import jdk.test.lib.ProcessTools;
+import jdk.test.lib.Utils;
 import java.util.ArrayList;
 import java.util.List;
 import java.util.Random;
 
 /**
- * The test verifies correctness of work {@link com.oracle.java.testlibrary.Utils#getRandomInstance()}.
+ * The test verifies correctness of work {@link jdk.test.lib.Utils#getRandomInstance()}.
  * Test works in three modes: same seed provided, no seed provided and
  * different seed provided. In the first case the test expects that all random numbers
  * will be repeated in all next iterations. For other two modes test expects that
--- a/hotspot/test/testlibrary_tests/RedefineClassTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/testlibrary_tests/RedefineClassTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,8 +33,8 @@
  * @run main/othervm -javaagent:redefineagent.jar RedefineClassTest
  */
 
-import static com.oracle.java.testlibrary.Asserts.*;
-import com.oracle.java.testlibrary.*;
+import static jdk.test.lib.Asserts.*;
+import jdk.test.lib.*;
 
 /*
  * Proof of concept test for the test utility class RedefineClassHelper
--- a/hotspot/test/testlibrary_tests/TestMutuallyExclusivePlatformPredicates.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/testlibrary_tests/TestMutuallyExclusivePlatformPredicates.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,8 +21,8 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.Platform;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.Platform;
 
 import java.lang.reflect.InvocationTargetException;
 import java.lang.reflect.Method;
@@ -36,7 +36,7 @@
 /**
  * @test
  * @summary Verify that for each group of mutually exclusive predicates defined
- *          in com.oracle.java.testlibrary.Platform one and only one predicate
+ *          in jdk.test.lib.Platform one and only one predicate
  *          evaluates to true.
  * @library /testlibrary
  * @modules java.base/sun.misc
@@ -72,7 +72,7 @@
 
     /**
      * Verifies that one and only one predicate method defined in
-     * {@link com.oracle.java.testlibrary.Platform}, whose name included into
+     * {@link jdk.test.lib.Platform}, whose name included into
      * methodGroup will return {@code true}.
      * @param methodGroup The group of methods that should be tested.
      */
@@ -91,7 +91,7 @@
 
     /**
      * Verifies that all predicates defined in
-     * {@link com.oracle.java.testlibrary.Platform} were either tested or
+     * {@link jdk.test.lib.Platform} were either tested or
      * explicitly ignored.
      */
     private static void verifyCoverage() {
@@ -112,7 +112,7 @@
 
     /**
      * Evaluates predicate method with name {@code name} defined in
-     * {@link com.oracle.java.testlibrary.Platform}.
+     * {@link jdk.test.lib.Platform}.
      *
      * @param name The name of a predicate to be evaluated.
      * @return evaluated predicate's value.
--- a/hotspot/test/testlibrary_tests/TestPlatformIsTieredSupported.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/testlibrary_tests/TestPlatformIsTieredSupported.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,8 +21,8 @@
  * questions.
  */
 
-import com.oracle.java.testlibrary.Asserts;
-import com.oracle.java.testlibrary.Platform;
+import jdk.test.lib.Asserts;
+import jdk.test.lib.Platform;
 import sun.hotspot.WhiteBox;
 
 /**
--- a/hotspot/test/testlibrary_tests/ctw/CtwTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/testlibrary_tests/ctw/CtwTest.java	Wed Jul 05 20:35:10 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
@@ -36,8 +36,8 @@
 import java.nio.file.StandardCopyOption;
 import java.nio.charset.Charset;
 
-import com.oracle.java.testlibrary.JDKToolFinder;
-import com.oracle.java.testlibrary.OutputAnalyzer;
+import jdk.test.lib.JDKToolFinder;
+import jdk.test.lib.OutputAnalyzer;
 
 public abstract class CtwTest {
     protected final String[] shouldContain;
--- a/hotspot/test/testlibrary_tests/ctw/JarDirTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/testlibrary_tests/ctw/JarDirTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build ClassFileInstaller com.oracle.java.testlibrary.* sun.hotspot.tools.ctw.CompileTheWorld sun.hotspot.WhiteBox Foo Bar
+ * @build ClassFileInstaller jdk.test.lib.* sun.hotspot.tools.ctw.CompileTheWorld sun.hotspot.WhiteBox Foo Bar
  * @run main ClassFileInstaller sun.hotspot.WhiteBox Foo Bar
  *                              sun.hotspot.WhiteBox$WhiteBoxPermission
  * @run main JarDirTest prepare
@@ -44,7 +44,7 @@
 import java.nio.file.Files;
 import java.nio.file.Paths;
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
+import jdk.test.lib.OutputAnalyzer;
 
 public class JarDirTest extends CtwTest {
     private static final String[] SHOULD_CONTAIN
--- a/hotspot/test/testlibrary_tests/ctw/JarsTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/testlibrary_tests/ctw/JarsTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
  *          java.compiler
  *          java.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build ClassFileInstaller com.oracle.java.testlibrary.* sun.hotspot.tools.ctw.CompileTheWorld sun.hotspot.WhiteBox Foo Bar
+ * @build ClassFileInstaller jdk.test.lib.* sun.hotspot.tools.ctw.CompileTheWorld sun.hotspot.WhiteBox Foo Bar
  * @run main ClassFileInstaller sun.hotspot.WhiteBox Foo Bar
  *                              sun.hotspot.WhiteBox$WhiteBoxPermission
  * @run main JarsTest prepare
@@ -40,7 +40,7 @@
  * @author igor.ignatyev@oracle.com
  */
 
-import com.oracle.java.testlibrary.OutputAnalyzer;
+import jdk.test.lib.OutputAnalyzer;
 
 public class JarsTest extends CtwTest {
     private static final String[] SHOULD_CONTAIN
--- a/hotspot/test/testlibrary_tests/whitebox/vm_flags/BooleanTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/testlibrary_tests/whitebox/vm_flags/BooleanTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,7 +29,7 @@
  *          java.compiler
  *          java.management/sun.management
  *          jdk.jvmstat/sun.jvmstat.monitor
- * @build BooleanTest ClassFileInstaller sun.hotspot.WhiteBox com.oracle.java.testlibrary.*
+ * @build BooleanTest ClassFileInstaller sun.hotspot.WhiteBox jdk.test.lib.*
  * @run main ClassFileInstaller sun.hotspot.WhiteBox
  *                              sun.hotspot.WhiteBox$WhiteBoxPermission
  * @run main/othervm/timeout=600 -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI BooleanTest
@@ -38,7 +38,7 @@
  */
 
 import sun.hotspot.WhiteBox;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import sun.management.*;
 import com.sun.management.*;
 
--- a/hotspot/test/testlibrary_tests/whitebox/vm_flags/SizeTTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/testlibrary_tests/whitebox/vm_flags/SizeTTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
  * @run main/othervm/timeout=600 -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI -XX:+UnlockExperimentalVMOptions SizeTTest
  * @summary testing of WB::set/getSizeTVMFlag()
  */
-import com.oracle.java.testlibrary.Platform;
+import jdk.test.lib.Platform;
 
 public class SizeTTest {
     private static final String FLAG_NAME = "ArrayAllocatorMallocLimit";
--- a/hotspot/test/testlibrary_tests/whitebox/vm_flags/UintxTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/testlibrary_tests/whitebox/vm_flags/UintxTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -34,7 +34,7 @@
  * @summary testing of WB::set/getUintxVMFlag()
  * @author igor.ignatyev@oracle.com
  */
-import com.oracle.java.testlibrary.Platform;
+import jdk.test.lib.Platform;
 
 public class UintxTest {
     private static final String FLAG_NAME = "VerifyGCStartAt";
--- a/hotspot/test/testlibrary_tests/whitebox/vm_flags/VmFlagTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/hotspot/test/testlibrary_tests/whitebox/vm_flags/VmFlagTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -26,7 +26,7 @@
 import sun.hotspot.WhiteBox;
 import sun.management.*;
 import com.sun.management.*;
-import com.oracle.java.testlibrary.*;
+import jdk.test.lib.*;
 import java.lang.management.ManagementFactory;
 
 public final class VmFlagTest<T> {
--- a/jaxp/.hgtags	Thu May 21 10:07:37 2015 -0700
+++ b/jaxp/.hgtags	Wed Jul 05 20:35:10 2017 +0200
@@ -307,3 +307,4 @@
 3bcf83c1bbc1b7663e930d72c133a9bd86c7618d jdk9-b62
 4a8f895f0317dcc90479cb7cc97014312e69edf7 jdk9-b63
 6f91749b5aaef1a171ec2254163233438d1071d1 jdk9-b64
+ae7406e82828fe1c245ac7507a9da5fd5b1c9529 jdk9-b65
--- a/jaxp/test/javax/xml/jaxp/TEST.properties	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,3 +0,0 @@
-# jaxp test uses TestNG
-TestNG.dirs = unittest
-
--- a/jaxp/test/javax/xml/jaxp/functional/test/auctionportal/AuctionController.java	Thu May 21 10:07:37 2015 -0700
+++ b/jaxp/test/javax/xml/jaxp/functional/test/auctionportal/AuctionController.java	Wed Jul 05 20:35:10 2017 +0200
@@ -22,8 +22,8 @@
  */
 package test.auctionportal;
 
-import static com.sun.org.apache.xerces.internal.jaxp.JAXPConstants.JAXP_SCHEMA_LANGUAGE;
-import static com.sun.org.apache.xerces.internal.jaxp.JAXPConstants.JAXP_SCHEMA_SOURCE;
+import static test.auctionportal.HiBidConstants.JAXP_SCHEMA_LANGUAGE;
+import static test.auctionportal.HiBidConstants.JAXP_SCHEMA_SOURCE;
 import static org.testng.Assert.assertEquals;
 import static org.testng.Assert.assertFalse;
 import static org.testng.Assert.assertTrue;
--- a/jaxp/test/javax/xml/jaxp/functional/test/auctionportal/AuctionItemRepository.java	Thu May 21 10:07:37 2015 -0700
+++ b/jaxp/test/javax/xml/jaxp/functional/test/auctionportal/AuctionItemRepository.java	Wed Jul 05 20:35:10 2017 +0200
@@ -22,10 +22,10 @@
  */
 package test.auctionportal;
 
-import static com.sun.org.apache.xerces.internal.impl.Constants.SP_ENTITY_EXPANSION_LIMIT;
-import static com.sun.org.apache.xerces.internal.impl.Constants.SP_MAX_OCCUR_LIMIT;
-import static com.sun.org.apache.xerces.internal.jaxp.JAXPConstants.JAXP_SCHEMA_LANGUAGE;
-import static com.sun.org.apache.xerces.internal.jaxp.JAXPConstants.JAXP_SCHEMA_SOURCE;
+import static test.auctionportal.HiBidConstants.SP_ENTITY_EXPANSION_LIMIT;
+import static test.auctionportal.HiBidConstants.SP_MAX_OCCUR_LIMIT;
+import static test.auctionportal.HiBidConstants.JAXP_SCHEMA_LANGUAGE;
+import static test.auctionportal.HiBidConstants.JAXP_SCHEMA_SOURCE;
 import static org.testng.Assert.assertTrue;
 import java.io.File;
 import java.io.FileInputStream;
--- a/jaxp/test/javax/xml/jaxp/functional/test/auctionportal/UserController.java	Thu May 21 10:07:37 2015 -0700
+++ b/jaxp/test/javax/xml/jaxp/functional/test/auctionportal/UserController.java	Wed Jul 05 20:35:10 2017 +0200
@@ -22,7 +22,7 @@
  */
 package test.auctionportal;
 
-import static com.sun.org.apache.xerces.internal.jaxp.JAXPConstants.JAXP_SCHEMA_LANGUAGE;
+import static test.auctionportal.HiBidConstants.JAXP_SCHEMA_LANGUAGE;
 import static org.testng.Assert.assertFalse;
 import java.io.FileOutputStream;
 import java.nio.file.Files;
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jaxp/test/javax/xml/jaxp/internaltest/TEST.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,3 @@
+# jaxp test uses TestNG
+TestNG.dirs = javax/xml/common/bug6979306 javax/xml/parsers/bug8003147 javax/xml/transform/bug6551616 javax/xml/transform/cli
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jaxp/test/javax/xml/jaxp/internaltest/javax/xml/common/bug6979306/Bug6979306Test.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,47 @@
+/*
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/*
+ * @test
+ * @modules java.xml/com.sun.org.apache.xerces.internal.impl
+ *          java.xml/com.sun.org.apache.xalan.internal
+ *          java.xml/com.sun.org.apache.xalan.internal.xslt
+ * @bug 6979306
+ * @summary Test JAXP component version.
+ */
+
+import org.testng.annotations.Test;
+
+import com.sun.org.apache.xalan.internal.xslt.EnvironmentCheck;
+
+public class Bug6979306Test {
+
+    @Test
+    public void test() {
+        String[] input = {};
+        EnvironmentCheck.main(input);
+        com.sun.org.apache.xerces.internal.impl.Version.main(input);
+        com.sun.org.apache.xalan.internal.Version._main(input);
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jaxp/test/javax/xml/jaxp/internaltest/javax/xml/parsers/bug8003147/Bug8003147Test.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,81 @@
+/*
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/*
+ * @test
+ * @modules java.xml/com.sun.org.apache.bcel.internal.classfile
+ *          java.xml/com.sun.org.apache.bcel.internal.generic
+ * @bug 8003147
+ * @summary Test port fix for BCEL bug 39695.
+ */
+
+import java.io.FileOutputStream;
+import java.util.ArrayList;
+
+import org.testng.Assert;
+import org.testng.annotations.Test;
+
+import com.sun.org.apache.bcel.internal.classfile.ClassParser;
+import com.sun.org.apache.bcel.internal.classfile.ConstantClass;
+import com.sun.org.apache.bcel.internal.classfile.ConstantPool;
+import com.sun.org.apache.bcel.internal.classfile.ConstantUtf8;
+import com.sun.org.apache.bcel.internal.classfile.JavaClass;
+import com.sun.org.apache.bcel.internal.classfile.Method;
+import com.sun.org.apache.bcel.internal.generic.ClassGen;
+import com.sun.org.apache.bcel.internal.generic.MethodGen;
+
+public class Bug8003147Test {
+
+    @Test
+    public void test() throws Exception {
+        String classfile = getClass().getResource("Bug8003147Test.class").getPath();
+        JavaClass jc = new ClassParser(classfile).parse();
+        // rename class
+        ConstantPool cp = jc.getConstantPool();
+        int cpIndex = ((ConstantClass) cp.getConstant(jc.getClassNameIndex())).getNameIndex();
+        cp.setConstant(cpIndex, new ConstantUtf8("Bug8003147TestPrime"));
+        ClassGen gen = new ClassGen(jc);
+        Method[] methods = jc.getMethods();
+        int index;
+        for (index = 0; index < methods.length; index++) {
+            if (methods[index].getName().equals("doSomething")) {
+                break;
+            }
+        }
+        Method m = methods[index];
+        MethodGen mg = new MethodGen(m, gen.getClassName(), gen.getConstantPool());
+        gen.replaceMethod(m, mg.getMethod());
+        String path = classfile.replace("Bug8003147Test", "Bug8003147TestPrime");
+        gen.getJavaClass().dump(new FileOutputStream(path));
+
+        try {
+            Class.forName("Bug8003147TestPrime");
+        } catch (ClassFormatError cfe) {
+            cfe.printStackTrace();
+            Assert.fail("modified version of class does not pass verification");
+        }
+    }
+
+    public void doSomething(double d, ArrayList<Integer> list) {
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jaxp/test/javax/xml/jaxp/internaltest/javax/xml/transform/bug6551616/Bug6551616.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,64 @@
+/*
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/*
+ * @test
+ * @modules java.xml/com.sun.org.apache.xalan.internal.xsltc.trax
+ * @bug 6551616
+ * @summary Test SAX2StAXEventWriter.
+ */
+
+import java.io.InputStream;
+import java.io.StringBufferInputStream;
+
+import javax.xml.stream.XMLEventWriter;
+import javax.xml.stream.XMLOutputFactory;
+
+import org.testng.annotations.Test;
+
+import com.sun.org.apache.xalan.internal.xsltc.trax.SAX2StAXEventWriter;
+
+public class Bug6551616 {
+    String _cache = "";
+
+
+    @Test
+    public void test() throws Exception {
+        final String XML = "" + "<?xml version='1.0'?>" + "<doc xmlns:foo='http://example.com/foo/' xml:lang='us-en'><p>Test</p></doc>";
+
+        javax.xml.parsers.SAXParserFactory saxFactory = javax.xml.parsers.SAXParserFactory.newInstance();
+
+        javax.xml.parsers.SAXParser parser = saxFactory.newSAXParser();
+
+        XMLOutputFactory outFactory = XMLOutputFactory.newInstance();
+        XMLEventWriter writer = outFactory.createXMLEventWriter(System.out);
+
+        SAX2StAXEventWriter handler = new SAX2StAXEventWriter(writer);
+
+        InputStream is = new StringBufferInputStream(XML);
+
+        parser.parse(is, handler);
+
+        // if it doesn't blow up, it succeeded.
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jaxp/test/javax/xml/jaxp/internaltest/javax/xml/transform/cli/CLITest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,45 @@
+/*
+ * Copyright (c) 2014, 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/*
+ * @test
+ * @modules java.xml/com.sun.org.apache.xalan.internal.xslt
+ * @summary Test internal transform CLI.
+ */
+
+import org.testng.Assert;
+import org.testng.annotations.Test;
+
+public class CLITest {
+
+    @Test
+    public void testCLI() {
+        try {
+            String[] args = new String[] { "-XSLTC", "-XSL", getClass().getResource("tigertest.xsl").toString(), "-IN",
+                    getClass().getResource("tigertest-in.xml").toString(), };
+            com.sun.org.apache.xalan.internal.xslt.Process._main(args);
+        } catch (Exception e) {
+            Assert.fail(e.getMessage());
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jaxp/test/javax/xml/jaxp/internaltest/javax/xml/transform/cli/tigertest-in.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,7 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<office:document xmlns:office="http://openoffice.org/2000/office" xmlns:style="http://openoffice.org/2000/style"  office:class="text" office:version="1.0">
+	<office:styles>
+		<style:default-style style:family="graphics"/>
+		<style:default-style style:family="paragraph"/>
+	</office:styles>
+</office:document>
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jaxp/test/javax/xml/jaxp/internaltest/javax/xml/transform/cli/tigertest.xsl	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,21 @@
+<?xml version='1.0' encoding="UTF-8"?>
+<xsl:stylesheet version="1.0"
+		xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
+		xmlns:office="http://openoffice.org/2000/office"
+		xmlns:style="http://openoffice.org/2000/style">
+
+	<xsl:output method="xml" encoding="UTF-8"/>
+
+	<xsl:template match="/">
+		<xsl:variable name="copyData">
+			<xsl:call-template name="copy-by-template" />
+		</xsl:variable>
+		<test>
+  		   <xsl:copy-of select="$copyData"/>
+		</test>
+	</xsl:template>
+
+	<xsl:template name="copy-by-template">
+		<xsl:copy-of select="/"/>
+	</xsl:template>
+</xsl:stylesheet>
--- a/jaxp/test/javax/xml/jaxp/libs/test/auctionportal/HiBidConstants.java	Thu May 21 10:07:37 2015 -0700
+++ b/jaxp/test/javax/xml/jaxp/libs/test/auctionportal/HiBidConstants.java	Wed Jul 05 20:35:10 2017 +0200
@@ -42,4 +42,24 @@
      * Name space for account operation.
      */
     public static final String PORTAL_ACCOUNT_NS = "http://www.auctionportal.org/Accounts";
+
+    /**
+     * JAXP schema language property name.
+     */
+    public static final String JAXP_SCHEMA_LANGUAGE = "http://java.sun.com/xml/jaxp/properties/schemaLanguage";
+
+    /**
+     * JAXP schema source property name.
+     */
+    public static final String JAXP_SCHEMA_SOURCE = "http://java.sun.com/xml/jaxp/properties/schemaSource";
+
+    /**
+     * Name of system property JDK entity expansion limit
+     */
+    public static final String SP_ENTITY_EXPANSION_LIMIT = "jdk.xml.entityExpansionLimit";
+
+    /**
+     * Name of system property JDK maxOccur limit
+     */
+    public static final String SP_MAX_OCCUR_LIMIT = "jdk.xml.maxOccurLimit";
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jaxp/test/javax/xml/jaxp/unittest/TEST.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,3 @@
+# jaxp test uses TestNG
+TestNG.dirs = .
+
--- a/jaxp/test/javax/xml/jaxp/unittest/javax/xml/common/Bug6979306Test.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,44 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package javax.xml.common;
-
-import org.testng.annotations.Test;
-
-import com.sun.org.apache.xalan.internal.xslt.EnvironmentCheck;
-
-/*
- * @bug 6979306
- * @summary Test JAXP component version.
- */
-public class Bug6979306Test {
-
-    @Test
-    public void test() {
-        String[] input = {};
-        EnvironmentCheck.main(input);
-        com.sun.org.apache.xerces.internal.impl.Version.main(input);
-        com.sun.org.apache.xalan.internal.Version._main(input);
-    }
-
-}
--- a/jaxp/test/javax/xml/jaxp/unittest/javax/xml/common/Bug7143711Test.java	Thu May 21 10:07:37 2015 -0700
+++ b/jaxp/test/javax/xml/jaxp/unittest/javax/xml/common/Bug7143711Test.java	Wed Jul 05 20:35:10 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
@@ -76,7 +76,7 @@
 
     }
 
-    @Test
+    @Test(enabled=false) //skipped due to bug JDK-8080097
     public void testTransform_DOM_withSM() {
         System.out.println("Transform using DOM Source;  Security Manager is set:");
 
@@ -89,7 +89,7 @@
             TransformerFactory factory = TransformerFactory.newInstance("com.sun.org.apache.xalan.internal.xsltc.trax.TransformerFactoryImpl",
                     TransformerFactory.class.getClassLoader());
             factory.setFeature(ORACLE_FEATURE_SERVICE_MECHANISM, true);
-            if (((com.sun.org.apache.xalan.internal.xsltc.trax.TransformerFactoryImpl) factory).useServicesMechnism()) {
+            if ((boolean) factory.getFeature(ORACLE_FEATURE_SERVICE_MECHANISM)) {
                 Assert.fail("should not override in secure mode");
             }
 
--- a/jaxp/test/javax/xml/jaxp/unittest/javax/xml/parsers/Bug8003147Test.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,79 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package javax.xml.parsers;
-
-import java.io.FileOutputStream;
-import java.util.ArrayList;
-
-import org.testng.Assert;
-import org.testng.annotations.Test;
-
-import com.sun.org.apache.bcel.internal.classfile.ClassParser;
-import com.sun.org.apache.bcel.internal.classfile.ConstantClass;
-import com.sun.org.apache.bcel.internal.classfile.ConstantPool;
-import com.sun.org.apache.bcel.internal.classfile.ConstantUtf8;
-import com.sun.org.apache.bcel.internal.classfile.JavaClass;
-import com.sun.org.apache.bcel.internal.classfile.Method;
-import com.sun.org.apache.bcel.internal.generic.ClassGen;
-import com.sun.org.apache.bcel.internal.generic.MethodGen;
-
-/*
- * @bug 8003147
- * @summary Test port fix for BCEL bug 39695.
- */
-public class Bug8003147Test {
-
-    @Test
-    public void test() throws Exception {
-        String classfile = getClass().getResource("Bug8003147Test.class").getPath();
-        JavaClass jc = new ClassParser(classfile).parse();
-        // rename class
-        ConstantPool cp = jc.getConstantPool();
-        int cpIndex = ((ConstantClass) cp.getConstant(jc.getClassNameIndex())).getNameIndex();
-        cp.setConstant(cpIndex, new ConstantUtf8("javax/xml/parsers/Bug8003147TestPrime"));
-        ClassGen gen = new ClassGen(jc);
-        Method[] methods = jc.getMethods();
-        int index;
-        for (index = 0; index < methods.length; index++) {
-            if (methods[index].getName().equals("doSomething")) {
-                break;
-            }
-        }
-        Method m = methods[index];
-        MethodGen mg = new MethodGen(m, gen.getClassName(), gen.getConstantPool());
-        gen.replaceMethod(m, mg.getMethod());
-        String path = classfile.replace("Bug8003147Test", "Bug8003147TestPrime");
-        gen.getJavaClass().dump(new FileOutputStream(path));
-
-        try {
-            Class.forName("javax.xml.parsers.Bug8003147TestPrime");
-        } catch (ClassFormatError cfe) {
-            cfe.printStackTrace();
-            Assert.fail("modified version of class does not pass verification");
-        }
-    }
-
-    public void doSomething(double d, ArrayList<Integer> list) {
-    }
-}
--- a/jaxp/test/javax/xml/jaxp/unittest/javax/xml/stream/XMLStreamWriterTest/NamespaceTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/jaxp/test/javax/xml/jaxp/unittest/javax/xml/stream/XMLStreamWriterTest/NamespaceTest.java	Wed Jul 05 20:35:10 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
@@ -24,20 +24,16 @@
 package javax.xml.stream.XMLStreamWriterTest;
 
 import java.io.ByteArrayOutputStream;
-import java.io.IOException;
 
 import javax.xml.XMLConstants;
 import javax.xml.stream.XMLOutputFactory;
 import javax.xml.stream.XMLStreamException;
 import javax.xml.stream.XMLStreamWriter;
-import javax.xml.transform.stream.StreamResult;
 
 import org.testng.Assert;
 import org.testng.annotations.BeforeMethod;
 import org.testng.annotations.Test;
 
-import com.sun.xml.internal.stream.writers.XMLStreamWriterImpl;
-
 /*
  * @summary Test the writing of Namespaces.
  */
@@ -80,15 +76,10 @@
     private void resetWriter() {
         // reset the Writer
         try {
-            xmlStreamWriter.flush();
-            xmlStreamWriter.close();
-            ((XMLStreamWriterImpl) xmlStreamWriter).reset();
             byteArrayOutputStream.reset();
-            ((XMLStreamWriterImpl) xmlStreamWriter).setOutput(new StreamResult(byteArrayOutputStream), "utf-8");
+            xmlStreamWriter = xmlOutputFactory.createXMLStreamWriter(byteArrayOutputStream, "utf-8");
         } catch (XMLStreamException xmlStreamException) {
             Assert.fail(xmlStreamException.toString());
-        } catch (IOException ioException) {
-            Assert.fail(ioException.toString());
         }
     }
 
--- a/jaxp/test/javax/xml/jaxp/unittest/javax/xml/transform/Bug6551616.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,65 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package javax.xml.transform;
-
-import java.io.File;
-import java.io.InputStream;
-import java.io.StringBufferInputStream;
-import java.security.Policy;
-
-import javax.xml.stream.XMLEventWriter;
-import javax.xml.stream.XMLOutputFactory;
-
-import com.sun.org.apache.xalan.internal.xsltc.trax.SAX2StAXEventWriter;
-
-import org.testng.annotations.Test;
-
-/*
- * @bug 6551616
- * @summary Test SAX2StAXEventWriter.
- */
-public class Bug6551616 {
-    String _cache = "";
-
-
-    @Test
-    public void test() throws Exception {
-        final String XML = "" + "<?xml version='1.0'?>" + "<doc xmlns:foo='http://example.com/foo/' xml:lang='us-en'><p>Test</p></doc>";
-
-        javax.xml.parsers.SAXParserFactory saxFactory = javax.xml.parsers.SAXParserFactory.newInstance();
-
-        javax.xml.parsers.SAXParser parser = saxFactory.newSAXParser();
-
-        XMLOutputFactory outFactory = XMLOutputFactory.newInstance();
-        XMLEventWriter writer = outFactory.createXMLEventWriter(System.out);
-
-        SAX2StAXEventWriter handler = new SAX2StAXEventWriter(writer);
-
-        InputStream is = new StringBufferInputStream(XML);
-
-        parser.parse(is, handler);
-
-        // if it doesn't blow up, it succeeded.
-    }
-}
--- a/jaxp/test/javax/xml/jaxp/unittest/javax/xml/transform/CLITest.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,44 +0,0 @@
-/*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-package javax.xml.transform;
-
-import org.testng.Assert;
-import org.testng.annotations.Test;
-
-/*
- * @summary Test internal transform CLI.
- */
-public class CLITest {
-
-    @Test
-    public void testCLI() {
-        try {
-            String[] args = new String[] { "-XSLTC", "-XSL", getClass().getResource("tigertest.xsl").toString(), "-IN",
-                    getClass().getResource("tigertest-in.xml").toString(), };
-            com.sun.org.apache.xalan.internal.xslt.Process._main(args);
-        } catch (Exception e) {
-            Assert.fail(e.getMessage());
-        }
-    }
-}
--- a/jaxp/test/javax/xml/jaxp/unittest/org/w3c/dom/ls/LSSerializerTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/jaxp/test/javax/xml/jaxp/unittest/org/w3c/dom/ls/LSSerializerTest.java	Wed Jul 05 20:35:10 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
@@ -42,12 +42,12 @@
 import org.xml.sax.InputSource;
 import org.xml.sax.SAXException;
 
-import com.sun.org.apache.xerces.internal.impl.Constants;
 
 /*
  * @summary Test LSSerializer.
  */
 public class LSSerializerTest {
+    private static final String DOM_FORMAT_PRETTY_PRINT = "format-pretty-print";
 
     class DOMErrorHandlerImpl implements DOMErrorHandler {
 
@@ -192,47 +192,47 @@
         DOMConfiguration domConfiguration = lsSerializer.getDomConfig();
 
         // query current configuration
-        Boolean defaultFormatPrettyPrint = (Boolean) domConfiguration.getParameter(Constants.DOM_FORMAT_PRETTY_PRINT);
-        Boolean canSetFormatPrettyPrintFalse = (Boolean) domConfiguration.canSetParameter(Constants.DOM_FORMAT_PRETTY_PRINT, Boolean.FALSE);
-        Boolean canSetFormatPrettyPrintTrue = (Boolean) domConfiguration.canSetParameter(Constants.DOM_FORMAT_PRETTY_PRINT, Boolean.TRUE);
+        Boolean defaultFormatPrettyPrint = (Boolean) domConfiguration.getParameter(DOM_FORMAT_PRETTY_PRINT);
+        Boolean canSetFormatPrettyPrintFalse = (Boolean) domConfiguration.canSetParameter(DOM_FORMAT_PRETTY_PRINT, Boolean.FALSE);
+        Boolean canSetFormatPrettyPrintTrue = (Boolean) domConfiguration.canSetParameter(DOM_FORMAT_PRETTY_PRINT, Boolean.TRUE);
 
-        System.out.println(Constants.DOM_FORMAT_PRETTY_PRINT + " default/can set false/can set true = " + defaultFormatPrettyPrint + "/"
+        System.out.println(DOM_FORMAT_PRETTY_PRINT + " default/can set false/can set true = " + defaultFormatPrettyPrint + "/"
                 + canSetFormatPrettyPrintFalse + "/" + canSetFormatPrettyPrintTrue);
 
         // test values
-        Assert.assertEquals(defaultFormatPrettyPrint, Boolean.FALSE, "Default value of " + Constants.DOM_FORMAT_PRETTY_PRINT + " should be " + Boolean.FALSE);
+        Assert.assertEquals(defaultFormatPrettyPrint, Boolean.FALSE, "Default value of " + DOM_FORMAT_PRETTY_PRINT + " should be " + Boolean.FALSE);
 
-        Assert.assertEquals(canSetFormatPrettyPrintFalse, Boolean.TRUE, "Can set " + Constants.DOM_FORMAT_PRETTY_PRINT + " to " + Boolean.FALSE + " should be "
+        Assert.assertEquals(canSetFormatPrettyPrintFalse, Boolean.TRUE, "Can set " + DOM_FORMAT_PRETTY_PRINT + " to " + Boolean.FALSE + " should be "
                 + Boolean.TRUE);
 
-        Assert.assertEquals(canSetFormatPrettyPrintTrue, Boolean.TRUE, "Can set " + Constants.DOM_FORMAT_PRETTY_PRINT + " to " + Boolean.TRUE + " should be "
+        Assert.assertEquals(canSetFormatPrettyPrintTrue, Boolean.TRUE, "Can set " + DOM_FORMAT_PRETTY_PRINT + " to " + Boolean.TRUE + " should be "
                 + Boolean.TRUE);
 
         // get default serialization
         String prettyPrintDefault = lsSerializer.writeToString(document);
-        System.out.println("(default) " + Constants.DOM_FORMAT_PRETTY_PRINT + "==" + (Boolean) domConfiguration.getParameter(Constants.DOM_FORMAT_PRETTY_PRINT)
+        System.out.println("(default) " + DOM_FORMAT_PRETTY_PRINT + "==" + (Boolean) domConfiguration.getParameter(DOM_FORMAT_PRETTY_PRINT)
                 + ": \n\"" + prettyPrintDefault + "\"");
 
-        Assert.assertEquals(XML_DOCUMENT_DEFAULT_PRINT, prettyPrintDefault, "Invalid serialization with default value, " + Constants.DOM_FORMAT_PRETTY_PRINT + "=="
-                + (Boolean) domConfiguration.getParameter(Constants.DOM_FORMAT_PRETTY_PRINT));
+        Assert.assertEquals(XML_DOCUMENT_DEFAULT_PRINT, prettyPrintDefault, "Invalid serialization with default value, " + DOM_FORMAT_PRETTY_PRINT + "=="
+                + (Boolean) domConfiguration.getParameter(DOM_FORMAT_PRETTY_PRINT));
 
         // configure LSSerializer to not format-pretty-print
-        domConfiguration.setParameter(Constants.DOM_FORMAT_PRETTY_PRINT, Boolean.FALSE);
+        domConfiguration.setParameter(DOM_FORMAT_PRETTY_PRINT, Boolean.FALSE);
         String prettyPrintFalse = lsSerializer.writeToString(document);
-        System.out.println("(FALSE) " + Constants.DOM_FORMAT_PRETTY_PRINT + "==" + (Boolean) domConfiguration.getParameter(Constants.DOM_FORMAT_PRETTY_PRINT)
+        System.out.println("(FALSE) " + DOM_FORMAT_PRETTY_PRINT + "==" + (Boolean) domConfiguration.getParameter(DOM_FORMAT_PRETTY_PRINT)
                 + ": \n\"" + prettyPrintFalse + "\"");
 
-        Assert.assertEquals(XML_DOCUMENT_DEFAULT_PRINT, prettyPrintFalse, "Invalid serialization with FALSE value, " + Constants.DOM_FORMAT_PRETTY_PRINT + "=="
-                + (Boolean) domConfiguration.getParameter(Constants.DOM_FORMAT_PRETTY_PRINT));
+        Assert.assertEquals(XML_DOCUMENT_DEFAULT_PRINT, prettyPrintFalse, "Invalid serialization with FALSE value, " + DOM_FORMAT_PRETTY_PRINT + "=="
+                + (Boolean) domConfiguration.getParameter(DOM_FORMAT_PRETTY_PRINT));
 
         // configure LSSerializer to format-pretty-print
-        domConfiguration.setParameter(Constants.DOM_FORMAT_PRETTY_PRINT, Boolean.TRUE);
+        domConfiguration.setParameter(DOM_FORMAT_PRETTY_PRINT, Boolean.TRUE);
         String prettyPrintTrue = lsSerializer.writeToString(document);
-        System.out.println("(TRUE) " + Constants.DOM_FORMAT_PRETTY_PRINT + "==" + (Boolean) domConfiguration.getParameter(Constants.DOM_FORMAT_PRETTY_PRINT)
+        System.out.println("(TRUE) " + DOM_FORMAT_PRETTY_PRINT + "==" + (Boolean) domConfiguration.getParameter(DOM_FORMAT_PRETTY_PRINT)
                 + ": \n\"" + prettyPrintTrue + "\"");
 
-        Assert.assertEquals(XML_DOCUMENT_PRETTY_PRINT, prettyPrintTrue, "Invalid serialization with TRUE value, " + Constants.DOM_FORMAT_PRETTY_PRINT + "=="
-                + (Boolean) domConfiguration.getParameter(Constants.DOM_FORMAT_PRETTY_PRINT));
+        Assert.assertEquals(XML_DOCUMENT_PRETTY_PRINT, prettyPrintTrue, "Invalid serialization with TRUE value, " + DOM_FORMAT_PRETTY_PRINT + "=="
+                + (Boolean) domConfiguration.getParameter(DOM_FORMAT_PRETTY_PRINT));
     }
 
     @Test
--- a/jdk/.hgtags	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/.hgtags	Wed Jul 05 20:35:10 2017 +0200
@@ -307,3 +307,4 @@
 49118e68fbd4cc0044e718c47db681946d5efd69 jdk9-b62
 fd3281c400347088b36aeb16273aa679d53a81a4 jdk9-b63
 7de8d036ad0980d988d1b9b4b4e6be555d9fbf98 jdk9-b64
+ed94f3e7ba6bbfec0772de6d24e39543e13f6d88 jdk9-b65
--- a/jdk/make/CompileDemos.gmk	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/make/CompileDemos.gmk	Wed Jul 05 20:35:10 2017 +0200
@@ -30,6 +30,7 @@
 include JavaCompilation.gmk
 include NativeCompilation.gmk
 include SetupJavaCompilers.gmk
+include TextFileProcessing.gmk
 
 # Prepare the find cache.
 $(eval $(call FillCacheFind, $(JDK_TOPDIR)/src))
@@ -49,6 +50,15 @@
 
 ##################################################################################################
 
+# This rule will be depended on due to the MANIFEST line
+$(eval $(call SetupTextFileProcessing, BUILD_JAVA_MANIFEST, \
+  SOURCE_FILES := $(JDK_TOPDIR)/make/data/mainmanifest/manifest.mf, \
+  OUTPUT_FILE := $(SUPPORT_OUTPUTDIR)/demo/java-main-manifest.mf, \
+  REPLACEMENTS := \
+      @@RELEASE@@ => $(RELEASE) ; \
+      @@COMPANY_NAME@@ => $(COMPANY_NAME) , \
+))
+
 define SetupAppletDemo
   $$(eval $$(call SetupJavaCompilation,BUILD_DEMO_APPLET_$1, \
       SETUP := GENERATE_USINGJDKBYTECODE, \
@@ -122,7 +132,7 @@
         COPY := $(PATTERNS_TO_COPY) $(10), \
         JAR := $(SUPPORT_OUTPUTDIR)/demo/image/$2/$1/$$($1_JARFILE), \
         JARMAIN := $4, \
-        MANIFEST := $(JDK_TOPDIR)/make/data/mainmanifest/manifest.mf, \
+        MANIFEST := $(SUPPORT_OUTPUTDIR)/demo/java-main-manifest.mf, \
         EXTRA_MANIFEST_ATTR := $(11), \
         SRCZIP := $(SUPPORT_OUTPUTDIR)/demo/image/$2/$1/src.zip, \
         EXCLUDE_FILES := $9, \
@@ -290,7 +300,7 @@
         COPY := $(PATTERNS_TO_COPY), \
         JAR := $(SUPPORT_OUTPUTDIR)/demo/image/jvmti/$1/$1.jar, \
         EXTRA_MANIFEST_ATTR := Main-Class: \n, \
-        MANIFEST := $(JDK_TOPDIR)/make/data/mainmanifest/manifest.mf))
+        MANIFEST := $(SUPPORT_OUTPUTDIR)/demo/java-main-manifest.mf))
 
     BUILD_DEMOS += $(SUPPORT_OUTPUTDIR)/demo/image/jvmti/$1/$1.jar
   endif
@@ -382,7 +392,7 @@
       BIN := $(SUPPORT_OUTPUTDIR)/demo/classes/jni/Poller, \
       HEADERS := $(SUPPORT_OUTPUTDIR)/demo/classes/jni/Poller, \
       JAR := $(SUPPORT_OUTPUTDIR)/demo/image/jni/Poller/Poller.jar, \
-      MANIFEST := $(JDK_TOPDIR)/make/data/mainmanifest/manifest.mf, \
+      MANIFEST := $(SUPPORT_OUTPUTDIR)/demo/java-main-manifest.mf, \
       SRCZIP := $(SUPPORT_OUTPUTDIR)/demo/image/jni/Poller/src.zip, \
       COPY := README.txt Poller.c, \
       JARMAIN := Client))
--- a/jdk/make/launcher/Launcher-jdk.dev.gmk	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/make/launcher/Launcher-jdk.dev.gmk	Wed Jul 05 20:35:10 2017 +0200
@@ -33,9 +33,6 @@
 $(eval $(call SetupLauncher,jimage,\
     -DJAVA_ARGS='{ "-J-ms8m"$(COMMA) "jdk.tools.jimage.Main"$(COMMA) }'))
 
-$(eval $(call SetupLauncher,jhat, \
-    -DJAVA_ARGS='{ "-J-ms8m"$(COMMA) "com.sun.tools.hat.Main"$(COMMA) }'))
-
 $(eval $(call SetupLauncher,native2ascii, \
     -DJAVA_ARGS='{ "-J-ms8m"$(COMMA) "sun.tools.native2ascii.Main"$(COMMA) }'))
 
--- a/jdk/make/lib/Lib-jdk.attach.gmk	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/make/lib/Lib-jdk.attach.gmk	Wed Jul 05 20:35:10 2017 +0200
@@ -27,6 +27,12 @@
 
 ################################################################################
 
+ifeq ($(OPENJDK_TARGET_OS), windows)
+  # In (at least) VS2013 and later, -DPSAPI_VERSION=1 is needed to generate
+  # a binary that is compatible with windows versions older than 7/2008R2.
+  # See MSDN documentation for GetProcessMemoryInfo for more information.
+  LIBATTACH_CFLAGS := -DPSAPI_VERSION=1
+endif
 
 $(eval $(call SetupNativeCompilation,BUILD_LIBATTACH, \
     LIBRARY := attach, \
@@ -35,7 +41,7 @@
     OPTIMIZATION := LOW, \
     CFLAGS := $(CFLAGS_JDKLIB) $(CFLAGS_WARNINGS_ARE_ERRORS) \
         -I$(SUPPORT_OUTPUTDIR)/headers/jdk.attach \
-        $(LIBJAVA_HEADER_FLAGS), \
+        $(LIBJAVA_HEADER_FLAGS) $(LIBATTACH_CFLAGS), \
     CFLAGS_windows := /Gy, \
     MAPFILE := $(JDK_TOPDIR)/make/mapfiles/libattach/mapfile-$(OPENJDK_TARGET_OS), \
     VERSIONINFO_RESOURCE := $(GLOBAL_VERSION_INFO_RESOURCE), \
--- a/jdk/make/lib/Lib-jdk.management.gmk	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/make/lib/Lib-jdk.management.gmk	Wed Jul 05 20:35:10 2017 +0200
@@ -39,10 +39,12 @@
     $(LIBJAVA_HEADER_FLAGS) \
     #
 
-# In (at least) VS2013 and later, -DPSAPI_VERSION=1 is needed to generate
-# a binary that is compatible with windows versions older than 7/2008R2.
-# See MSDN documentation for GetProcessMemoryInfo for more information.
-BUILD_LIBMANAGEMENT_EXT_CFLAGS += -DPSAPI_VERSION=1
+ifeq ($(OPENJDK_TARGET_OS), windows)
+  # In (at least) VS2013 and later, -DPSAPI_VERSION=1 is needed to generate
+  # a binary that is compatible with windows versions older than 7/2008R2.
+  # See MSDN documentation for GetProcessMemoryInfo for more information.
+  LIBMANAGEMENT_EXT_CFLAGS += -DPSAPI_VERSION=1
+endif
 
 LIBMANAGEMENT_EXT_OPTIMIZATION := HIGH
 ifneq ($(findstring $(OPENJDK_TARGET_OS), solaris linux), )
--- a/jdk/make/src/classes/build/tools/module/boot.modules	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/make/src/classes/build/tools/module/boot.modules	Wed Jul 05 20:35:10 2017 +0200
@@ -24,6 +24,7 @@
 jdk.jfr
 jdk.management
 jdk.management.cmm
+jdk.management.resource
 jdk.naming.rmi
 jdk.sctp
 jdk.security.auth
--- a/jdk/src/demo/share/applets.html	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/demo/share/applets.html	Wed Jul 05 20:35:10 2017 +0200
@@ -56,8 +56,7 @@
 </TR>
 
 <TR>
-<TD ALIGN=RIGHT COLSPAN="2"><!-- page headline --><!-------------------------------><!--EDIT THE PAGE HEADLINE HERE--><!------------BEGIN-HEADLINE-----><FONT SIZE=+2>JAVA</FONT><SUP><FONT SIZE=-2>TM</FONT></SUP><FONT SIZE=+2>
-PLUG-IN</FONT> &nbsp;
+<TD ALIGN=RIGHT COLSPAN="2"><!-- page headline --><!-------------------------------><!--EDIT THE PAGE HEADLINE HERE--><!------------BEGIN-HEADLINE-----><FONT SIZE=+2>JAVA&trade; PLUG-IN</FONT> &nbsp;
 <BR><B>Demonstration Applets</B>&nbsp;
 <BR><!-------------END-HEADLINE------><!--    END OF PAGE HEADLINE   --><!-------------------------------></TD>
 </TR>
--- a/jdk/src/demo/share/jvmti/index.html	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/demo/share/jvmti/index.html	Wed Jul 05 20:35:10 2017 +0200
@@ -5,7 +5,7 @@
 
 <p>
 The 
-Java<sup><font size=-2>TM</font></sup> Virtual Machine Tools Interface (JVM TI)
+Java&trade; Virtual Machine Tools Interface (JVM TI)
 is a native tool interface provided in JDK 5.0 and newer.
 Native libraries that use JVM TI and are loaded into the 
 Java Virtual Machine
--- a/jdk/src/java.base/share/classes/java/lang/Boolean.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/Boolean.java	Wed Jul 05 20:35:10 2017 +0200
@@ -230,13 +230,12 @@
     }
 
     /**
-     * Returns {@code true} if and only if the system property
-     * named by the argument exists and is equal to the string
-     * {@code "true"}. (Beginning with version 1.0.2 of the
-     * Java<small><sup>TM</sup></small> platform, the test of
-     * this string is case insensitive.) A system property is accessible
-     * through {@code getProperty}, a method defined by the
-     * {@code System} class.
+     * Returns {@code true} if and only if the system property named
+     * by the argument exists and is equal to the string {@code
+     * "true"}. (Beginning with version 1.0.2 of the Java&trade;
+     * platform, the test of this string is case insensitive.) A
+     * system property is accessible through {@code getProperty}, a
+     * method defined by the {@code System} class.
      * <p>
      * If there is no property with the specified name, or if the specified
      * name is empty or null, then {@code false} is returned.
--- a/jdk/src/java.base/share/classes/java/lang/Character.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/Character.java	Wed Jul 05 20:35:10 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
@@ -645,8 +645,14 @@
      * @since 1.2
      */
     public static final class UnicodeBlock extends Subset {
-
-        private static Map<String, UnicodeBlock> map = new HashMap<>(256);
+        /**
+         * 510  - the expected number of enteties
+         * 0.75 - the default load factor of HashMap
+         */
+        private static final int INITIAL_CAPACITY =
+                (int)(510 / 0.75f + 1.0f);
+        private static Map<String, UnicodeBlock> map =
+                new HashMap<>(INITIAL_CAPACITY);
 
         /**
          * Creates a UnicodeBlock with the given identifier name.
--- a/jdk/src/java.base/share/classes/java/lang/Long.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/Long.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1708,7 +1708,7 @@
      * @since 1.5
      */
      public static int bitCount(long i) {
-        // HD, Figure 5-14
+        // HD, Figure 5-2
         i = i - ((i >>> 1) & 0x5555555555555555L);
         i = (i & 0x3333333333333333L) + ((i >>> 2) & 0x3333333333333333L);
         i = (i + (i >>> 4)) & 0x0f0f0f0f0f0f0f0fL;
--- a/jdk/src/java.base/share/classes/java/lang/String.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/lang/String.java	Wed Jul 05 20:35:10 2017 +0200
@@ -179,7 +179,7 @@
      * not affect the newly created string.
      *
      * @param  value
-         *         Array that is the source of characters
+     *         Array that is the source of characters
      *
      * @param  offset
      *         The initial offset
@@ -208,7 +208,7 @@
         if (offset > value.length - count) {
             throw new StringIndexOutOfBoundsException(offset + count);
         }
-        this.value = Arrays.copyOfRange(value, offset, offset+count);
+        this.value = Arrays.copyOfRange(value, offset, offset + count);
     }
 
     /**
@@ -262,11 +262,11 @@
         // Pass 1: Compute precise size of char[]
         int n = count;
         for (int i = offset; i < end; i++) {
-        int c = codePoints[i];
-        if (Character.isBmpCodePoint(c))
-            continue;
-        else if (Character.isValidCodePoint(c))
-            n++;
+            int c = codePoints[i];
+            if (Character.isBmpCodePoint(c))
+                continue;
+            else if (Character.isValidCodePoint(c))
+                n++;
             else throw new IllegalArgumentException(Integer.toString(c));
         }
 
@@ -327,7 +327,7 @@
     @Deprecated
     public String(byte ascii[], int hibyte, int offset, int count) {
         checkBounds(ascii, offset, count);
-        char value[] = new char[count];
+        char[] value = new char[count];
 
         if (hibyte == 0) {
             for (int i = count; i-- > 0;) {
@@ -465,7 +465,7 @@
         if (charset == null)
             throw new NullPointerException("charset");
         checkBounds(bytes, offset, length);
-        this.value =  StringCoding.decode(charset, bytes, offset, length);
+        this.value = StringCoding.decode(charset, bytes, offset, length);
     }
 
     /**
@@ -567,7 +567,7 @@
      *
      * @since  1.1
      */
-    public String(byte bytes[]) {
+    public String(byte[] bytes) {
         this(bytes, 0, bytes.length);
     }
 
@@ -983,11 +983,10 @@
             return true;
         }
         if (anObject instanceof String) {
-            String anotherString = (String)anObject;
-            int n = value.length;
-            if (n == anotherString.value.length) {
-                char v1[] = value;
-                char v2[] = anotherString.value;
+            char[] v1 = value;
+            char[] v2 = ((String)anObject).value;
+            int n = v1.length;
+            if (n == v2.length) {
                 int i = 0;
                 while (n-- != 0) {
                     if (v1[i] != v2[i])
@@ -1020,8 +1019,8 @@
     }
 
     private boolean nonSyncContentEquals(AbstractStringBuilder sb) {
-        char v1[] = value;
-        char v2[] = sb.getValue();
+        char[] v1 = value;
+        char[] v2 = sb.getValue();
         int n = v1.length;
         if (n != sb.length()) {
             return false;
@@ -1066,7 +1065,7 @@
             return equals(cs);
         }
         // Argument is a generic CharSequence
-        char v1[] = value;
+        char[] v1 = value;
         int n = v1.length;
         if (n != cs.length()) {
             return false;
@@ -1156,20 +1155,18 @@
      *          lexicographically greater than the string argument.
      */
     public int compareTo(String anotherString) {
-        int len1 = value.length;
-        int len2 = anotherString.value.length;
+        char[] v1 = value;
+        char[] v2 = anotherString.value;
+        int len1 = v1.length;
+        int len2 = v2.length;
         int lim = Math.min(len1, len2);
-        char v1[] = value;
-        char v2[] = anotherString.value;
 
-        int k = 0;
-        while (k < lim) {
+        for (int k = 0; k < lim; k++) {
             char c1 = v1[k];
             char c2 = v2[k];
             if (c1 != c2) {
                 return c1 - c2;
             }
-            k++;
         }
         return len1 - len2;
     }
@@ -1278,14 +1275,14 @@
      */
     public boolean regionMatches(int toffset, String other, int ooffset,
             int len) {
-        char ta[] = value;
+        char[] ta = value;
         int to = toffset;
-        char pa[] = other.value;
+        char[] pa = other.value;
         int po = ooffset;
         // Note: toffset, ooffset, or len might be near -1>>>1.
         if ((ooffset < 0) || (toffset < 0)
-                || (toffset > (long)value.length - len)
-                || (ooffset > (long)other.value.length - len)) {
+                || (toffset > (long)ta.length - len)
+                || (ooffset > (long)pa.length - len)) {
             return false;
         }
         while (len-- > 0) {
@@ -1348,14 +1345,14 @@
      */
     public boolean regionMatches(boolean ignoreCase, int toffset,
             String other, int ooffset, int len) {
-        char ta[] = value;
+        char[] ta = value;
         int to = toffset;
-        char pa[] = other.value;
+        char[] pa = other.value;
         int po = ooffset;
         // Note: toffset, ooffset, or len might be near -1>>>1.
         if ((ooffset < 0) || (toffset < 0)
-                || (toffset > (long)value.length - len)
-                || (ooffset > (long)other.value.length - len)) {
+                || (toffset > (long)ta.length - len)
+                || (ooffset > (long)pa.length - len)) {
             return false;
         }
         while (len-- > 0) {
@@ -1405,13 +1402,13 @@
      *          </pre>
      */
     public boolean startsWith(String prefix, int toffset) {
-        char ta[] = value;
+        char[] ta = value;
         int to = toffset;
-        char pa[] = prefix.value;
+        char[] pa = prefix.value;
         int po = 0;
-        int pc = prefix.value.length;
+        int pc = pa.length;
         // Note: toffset might be near -1>>>1.
-        if ((toffset < 0) || (toffset > value.length - pc)) {
+        if ((toffset < 0) || (toffset > ta.length - pc)) {
             return false;
         }
         while (--pc >= 0) {
@@ -1473,7 +1470,9 @@
             for (char v : value) {
                 h = 31 * h + v;
             }
-            hash = h;
+            if (h != 0) {
+                hash = h;
+            }
         }
         return h;
     }
@@ -1928,14 +1927,17 @@
      *             length of this {@code String} object.
      */
     public String substring(int beginIndex) {
-        if (beginIndex < 0) {
-            throw new StringIndexOutOfBoundsException(beginIndex);
+        if (beginIndex <= 0) {
+            if (beginIndex < 0) {
+                throw new StringIndexOutOfBoundsException(beginIndex);
+            }
+            return this;
         }
         int subLen = value.length - beginIndex;
         if (subLen < 0) {
             throw new StringIndexOutOfBoundsException(subLen);
         }
-        return (beginIndex == 0) ? this : new String(value, beginIndex, subLen);
+        return new String(value, beginIndex, subLen);
     }
 
     /**
@@ -1961,8 +1963,13 @@
      *             {@code endIndex}.
      */
     public String substring(int beginIndex, int endIndex) {
-        if (beginIndex < 0) {
-            throw new StringIndexOutOfBoundsException(beginIndex);
+        if (beginIndex <= 0) {
+            if (beginIndex < 0) {
+                throw new StringIndexOutOfBoundsException(beginIndex);
+            }
+            if (endIndex == value.length) {
+                return this;
+            }
         }
         if (endIndex > value.length) {
             throw new StringIndexOutOfBoundsException(endIndex);
@@ -1971,8 +1978,7 @@
         if (subLen < 0) {
             throw new StringIndexOutOfBoundsException(subLen);
         }
-        return ((beginIndex == 0) && (endIndex == value.length)) ? this
-                : new String(value, beginIndex, subLen);
+        return new String(value, beginIndex, subLen);
     }
 
     /**
@@ -2034,7 +2040,7 @@
             return this;
         }
         int len = value.length;
-        char buf[] = Arrays.copyOf(value, len + otherLen);
+        char[] buf = Arrays.copyOf(value, len + otherLen);
         str.getChars(buf, len);
         return new String(buf, true);
     }
@@ -2070,9 +2076,9 @@
      */
     public String replace(char oldChar, char newChar) {
         if (oldChar != newChar) {
-            int len = value.length;
+            char[] val = value; /* avoid getfield opcode */
+            int len = val.length;
             int i = -1;
-            char[] val = value; /* avoid getfield opcode */
 
             while (++i < len) {
                 if (val[i] == oldChar) {
@@ -2080,7 +2086,7 @@
                 }
             }
             if (i < len) {
-                char buf[] = new char[len];
+                char[] buf = new char[len];
                 for (int j = 0; j < i; j++) {
                     buf[j] = val[j];
                 }
@@ -2876,17 +2882,17 @@
      *          trailing white space.
      */
     public String trim() {
-        int len = value.length;
-        int st = 0;
         char[] val = value;    /* avoid getfield opcode */
+        int end = val.length;
+        int beg = 0;
 
-        while ((st < len) && (val[st] <= ' ')) {
-            st++;
+        while ((beg < end) && (val[beg] <= ' ')) {
+            beg++;
         }
-        while ((st < len) && (val[len - 1] <= ' ')) {
-            len--;
+        while ((beg < end) && (val[end - 1] <= ' ')) {
+            end--;
         }
-        return ((st > 0) || (len < value.length)) ? substring(st, len) : this;
+        return substring(beg, end);
     }
 
     /**
@@ -3081,7 +3087,7 @@
      */
     public char[] toCharArray() {
         // Cannot use Arrays.copyOf because of class initialization order issues
-        char result[] = new char[value.length];
+        char[] result = new char[value.length];
         System.arraycopy(value, 0, result, 0, value.length);
         return result;
     }
@@ -3266,8 +3272,7 @@
      *          as its single character the argument {@code c}.
      */
     public static String valueOf(char c) {
-        char data[] = {c};
-        return new String(data, true);
+        return new String(new char[]{c}, true);
     }
 
     /**
--- a/jdk/src/java.base/share/classes/java/security/ProtectionDomain.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/security/ProtectionDomain.java	Wed Jul 05 20:35:10 2017 +0200
@@ -25,23 +25,24 @@
 
 package java.security;
 
+import java.lang.ref.Reference;
+import java.lang.ref.ReferenceQueue;
 import java.lang.ref.WeakReference;
 import java.util.ArrayList;
 import java.util.Enumeration;
 import java.util.List;
 import java.util.Map;
 import java.util.WeakHashMap;
+import java.util.concurrent.ConcurrentHashMap;
+import sun.misc.JavaSecurityAccess;
 import sun.misc.JavaSecurityProtectionDomainAccess;
 import static sun.misc.JavaSecurityProtectionDomainAccess.ProtectionDomainCache;
+import sun.misc.SharedSecrets;
 import sun.security.util.Debug;
 import sun.security.util.SecurityConstants;
-import sun.misc.JavaSecurityAccess;
-import sun.misc.SharedSecrets;
 
 /**
- *
- *<p>
- * This ProtectionDomain class encapsulates the characteristics of a domain,
+ * The ProtectionDomain class encapsulates the characteristics of a domain,
  * which encloses a set of classes whose instances are granted a set
  * of permissions when being executed on behalf of a given set of Principals.
  * <p>
@@ -58,6 +59,7 @@
  */
 
 public class ProtectionDomain {
+
     private static class JavaSecurityAccessImpl implements JavaSecurityAccess {
 
         private JavaSecurityAccessImpl() {
@@ -86,18 +88,33 @@
                 AccessController.getContext(), context);
         }
 
-        private static AccessControlContext getCombinedACC(AccessControlContext context, AccessControlContext stack) {
-            AccessControlContext acc = new AccessControlContext(context, stack.getCombiner(), true);
+        private static AccessControlContext getCombinedACC(
+            AccessControlContext context, AccessControlContext stack) {
+            AccessControlContext acc =
+                new AccessControlContext(context, stack.getCombiner(), true);
 
             return new AccessControlContext(stack.getContext(), acc).optimize();
         }
     }
 
     static {
-        // Set up JavaSecurityAccess in SharedSecrets
+        // setup SharedSecrets to allow access to doIntersectionPrivilege
+        // methods and ProtectionDomain cache
         SharedSecrets.setJavaSecurityAccess(new JavaSecurityAccessImpl());
+        SharedSecrets.setJavaSecurityProtectionDomainAccess(
+            new JavaSecurityProtectionDomainAccess() {
+                @Override
+                public ProtectionDomainCache getProtectionDomainCache() {
+                    return new PDCache();
+                }
+            });
     }
 
+    /**
+     * Used for storing ProtectionDomains as keys in a Map.
+     */
+    static final class Key {}
+
     /* CodeSource */
     private CodeSource codesource ;
 
@@ -451,40 +468,104 @@
     }
 
     /**
-     * Used for storing ProtectionDomains as keys in a Map.
+     * A cache of ProtectionDomains and their Permissions.
+     *
+     * This class stores ProtectionDomains as weak keys in a ConcurrentHashMap
+     * with additional support for checking and removing weak keys that are no
+     * longer in use.
      */
-    final static class Key {}
-
-    // A cache of ProtectionDomains and their Permissions
     private static class PDCache implements ProtectionDomainCache {
-        // We must wrap the PermissionCollection in a WeakReference as there
-        // are some PermissionCollections which contain strong references
-        // back to a ProtectionDomain and otherwise would never be removed
-        // from the WeakHashMap
-        private final Map<Key, WeakReference<PermissionCollection>>
-            map = new WeakHashMap<>();
+        private final ConcurrentHashMap<WeakProtectionDomainKey,
+                                        PermissionCollection>
+                                        pdMap = new ConcurrentHashMap<>();
+        private final ReferenceQueue<Key> queue = new ReferenceQueue<>();
 
         @Override
-        public synchronized void put(ProtectionDomain pd,
-                                     PermissionCollection pc) {
-            map.put(pd == null ? null : pd.key, new WeakReference<>(pc));
+        public void put(ProtectionDomain pd, PermissionCollection pc) {
+            processQueue(queue, pdMap);
+            WeakProtectionDomainKey weakPd =
+                new WeakProtectionDomainKey(pd, queue);
+            pdMap.putIfAbsent(weakPd, pc);
         }
 
         @Override
-        public synchronized PermissionCollection get(ProtectionDomain pd) {
-            WeakReference<PermissionCollection> ref =
-                map.get(pd == null ? null : pd.key);
-            return ref == null ? null : ref.get();
+        public PermissionCollection get(ProtectionDomain pd) {
+            processQueue(queue, pdMap);
+            WeakProtectionDomainKey weakPd =
+                new WeakProtectionDomainKey(pd, queue);
+            return pdMap.get(weakPd);
+        }
+
+        /**
+         * Removes weak keys from the map that have been enqueued
+         * on the reference queue and are no longer in use.
+         */
+        private static void processQueue(ReferenceQueue<Key> queue,
+                                         ConcurrentHashMap<? extends
+                                         WeakReference<Key>, ?> pdMap) {
+            Reference<? extends Key> ref;
+            while ((ref = queue.poll()) != null) {
+                pdMap.remove(ref);
+            }
         }
     }
 
-    static {
-        SharedSecrets.setJavaSecurityProtectionDomainAccess(
-            new JavaSecurityProtectionDomainAccess() {
-                @Override
-                public ProtectionDomainCache getProtectionDomainCache() {
-                    return new PDCache();
-                }
-            });
+    /**
+     * A weak key for a ProtectionDomain.
+     */
+    private static class WeakProtectionDomainKey extends WeakReference<Key> {
+        /**
+         * Saved value of the referent's identity hash code, to maintain
+         * a consistent hash code after the referent has been cleared
+         */
+        private final int hash;
+
+        /**
+         * A key representing a null ProtectionDomain.
+         */
+        private static final Key NULL_KEY = new Key();
+
+        /**
+         * Create a new WeakProtectionDomain with the specified domain and
+         * registered with a queue.
+         */
+        WeakProtectionDomainKey(ProtectionDomain pd, ReferenceQueue<Key> rq) {
+            this((pd == null ? NULL_KEY : pd.key), rq);
+        }
+
+        private WeakProtectionDomainKey(Key key, ReferenceQueue<Key> rq) {
+            super(key, rq);
+            hash = key.hashCode();
+        }
+
+        /**
+         * Returns the identity hash code of the original referent.
+         */
+        @Override
+        public int hashCode() {
+            return hash;
+        }
+
+        /**
+         * Returns true if the given object is an identical
+         * WeakProtectionDomainKey instance, or, if this object's referent
+         * has not been cleared and the given object is another
+         * WeakProtectionDomainKey instance with an identical non-null
+         * referent as this one.
+         */
+        @Override
+        public boolean equals(Object obj) {
+            if (obj == this) {
+                return true;
+            }
+
+            if (obj instanceof WeakProtectionDomainKey) {
+                Object referent = get();
+                return (referent != null) &&
+                       (referent == ((WeakProtectionDomainKey)obj).get());
+            } else {
+                return false;
+            }
+        }
     }
 }
--- a/jdk/src/java.base/share/classes/java/text/ChoiceFormat.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/text/ChoiceFormat.java	Wed Jul 05 20:35:10 2017 +0200
@@ -490,7 +490,7 @@
     }
 
     /**
-     * Equality comparision between two
+     * Equality comparison between two
      */
     public boolean equals(Object obj) {
         if (obj == null) return false;
--- a/jdk/src/java.base/share/classes/java/util/ArrayPrefixHelpers.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/ArrayPrefixHelpers.java	Wed Jul 05 20:35:10 2017 +0200
@@ -85,7 +85,7 @@
      *
      * As usual for this sort of utility, there are 4 versions, that
      * are simple copy/paste/adapt variants of each other.  (The
-     * double and int versions differ from long version soley by
+     * double and int versions differ from long version solely by
      * replacing "long" (with case-matching)).
      */
 
--- a/jdk/src/java.base/share/classes/java/util/Calendar.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/Calendar.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1172,7 +1172,7 @@
          * {@code fieldValuePairs} that are pairs of a field and its value.
          * For example,
          * <pre>
-         *   setFeilds(Calendar.YEAR, 2013,
+         *   setFields(Calendar.YEAR, 2013,
          *             Calendar.MONTH, Calendar.DECEMBER,
          *             Calendar.DAY_OF_MONTH, 23);</pre>
          * is equivalent to the sequence of the following
@@ -1298,7 +1298,7 @@
 
         /**
          * Sets the time zone parameter to the given {@code zone}. If no time
-         * zone parameter is given to this {@code Caledar.Builder}, the
+         * zone parameter is given to this {@code Calendar.Builder}, the
          * {@linkplain TimeZone#getDefault() default
          * <code>TimeZone</code>} will be used in the {@link #build() build}
          * method.
@@ -3316,7 +3316,7 @@
      * @param field the calendar field
      * @return the calendar field name
      * @exception IndexOutOfBoundsException if <code>field</code> is negative,
-     * equal to or greater then <code>FIELD_COUNT</code>.
+     * equal to or greater than {@code FIELD_COUNT}.
      */
     static String getFieldName(int field) {
         return FIELD_NAME[field];
--- a/jdk/src/java.base/share/classes/java/util/Collection.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/Collection.java	Wed Jul 05 20:35:10 2017 +0200
@@ -537,7 +537,7 @@
      * @implSpec
      * The default implementation creates a
      * <em><a href="Spliterator.html#binding">late-binding</a></em> spliterator
-     * from the collections's {@code Iterator}.  The spliterator inherits the
+     * from the collection's {@code Iterator}.  The spliterator inherits the
      * <em>fail-fast</em> properties of the collection's iterator.
      * <p>
      * The created {@code Spliterator} reports {@link Spliterator#SIZED}.
--- a/jdk/src/java.base/share/classes/java/util/Locale.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/Locale.java	Wed Jul 05 20:35:10 2017 +0200
@@ -719,7 +719,7 @@
      * created and cached.
      *
      * @param language lowercase 2 to 8 language code.
-     * @param country uppercase two-letter ISO-3166 code and numric-3 UN M.49 area code.
+     * @param country uppercase two-letter ISO-3166 code and numeric-3 UN M.49 area code.
      * @param variant vendor and browser specific code. See class description.
      * @return the <code>Locale</code> instance requested
      * @exception NullPointerException if any argument is null.
@@ -1236,7 +1236,7 @@
     /**
      * Package private method returning the Locale's LocaleExtensions,
      * used by ResourceBundle.
-     * @return locale exnteions of this Locale,
+     * @return locale extensions of this Locale,
      *         or {@code null} if no extensions are defined
      */
      LocaleExtensions getLocaleExtensions() {
@@ -2609,7 +2609,7 @@
          * href="./Locale.html#def_locale_extension">well-formed</a> or an exception
          * is thrown.
          *
-         * <p>Attribute comparision for removal is case-insensitive.
+         * <p>Attribute comparison for removal is case-insensitive.
          *
          * @param attribute the attribute
          * @return This builder.
--- a/jdk/src/java.base/share/classes/java/util/TimeZone.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/TimeZone.java	Wed Jul 05 20:35:10 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
@@ -293,6 +293,7 @@
             throw new NullPointerException();
         }
         this.ID = ID;
+        this.zoneId = null;   // invalidate cache
     }
 
     /**
@@ -544,7 +545,23 @@
      * @since 1.8
      */
     public ZoneId toZoneId() {
+        ZoneId zId = zoneId;
+        if (zId == null) {
+            zoneId = zId = toZoneId0();
+        }
+        return zId;
+    }
+
+    private ZoneId toZoneId0() {
         String id = getID();
+        TimeZone defaultZone = defaultTimeZone;
+        // are we not defaultTimeZone but our id is equal to default's?
+        if (defaultZone != this &&
+            defaultZone != null && id.equals(defaultZone.getID())) {
+            // delegate to default TZ which is effectively immutable
+            return defaultZone.toZoneId();
+        }
+        // derive it ourselves
         if (ZoneInfoFile.useOldMapping() && id.length() == 3) {
             if ("EST".equals(id))
                 return ZoneId.of("America/New_York");
@@ -710,7 +727,12 @@
             sm.checkPermission(new PropertyPermission
                                ("user.timezone", "write"));
         }
-        defaultTimeZone = zone;
+        // by saving a defensive clone and returning a clone in getDefault() too,
+        // the defaultTimeZone instance is isolated from user code which makes it
+        // effectively immutable. This is important to avoid races when the
+        // following is evaluated in ZoneId.systemDefault():
+        // TimeZone.getDefault().toZoneId().
+        defaultTimeZone = (zone == null) ? null : (TimeZone) zone.clone();
     }
 
     /**
@@ -735,9 +757,7 @@
     public Object clone()
     {
         try {
-            TimeZone other = (TimeZone) super.clone();
-            other.ID = ID;
-            return other;
+            return super.clone();
         } catch (CloneNotSupportedException e) {
             throw new InternalError(e);
         }
@@ -759,6 +779,12 @@
      * @serial
      */
     private String           ID;
+
+    /**
+     * Cached {@link ZoneId} for this TimeZone
+     */
+    private transient ZoneId zoneId;
+
     private static volatile TimeZone defaultTimeZone;
 
     static final String         GMT_ID        = "GMT";
--- a/jdk/src/java.base/share/classes/java/util/TreeMap.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/TreeMap.java	Wed Jul 05 20:35:10 2017 +0200
@@ -859,7 +859,7 @@
      * Returns a {@link Set} view of the mappings contained in this map.
      *
      * <p>The set's iterator returns the entries in ascending key order. The
-     * sets's spliterator is
+     * set's spliterator is
      * <em><a href="Spliterator.html#binding">late-binding</a></em>,
      * <em>fail-fast</em>, and additionally reports {@link Spliterator#SORTED} and
      * {@link Spliterator#ORDERED} with an encounter order that is ascending key
@@ -2643,7 +2643,7 @@
      * child, also serving as origin for the split-off spliterator.
      * Left-hands are symmetric. Descending versions place the origin
      * at the end and invert ascending split rules.  This base class
-     * is non-commital about directionality, or whether the top-level
+     * is non-committal about directionality, or whether the top-level
      * spliterator covers the whole tree. This means that the actual
      * split mechanics are located in subclasses. Some of the subclass
      * trySplit methods are identical (except for return types), but
--- a/jdk/src/java.base/share/classes/java/util/concurrent/ConcurrentHashMap.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/concurrent/ConcurrentHashMap.java	Wed Jul 05 20:35:10 2017 +0200
@@ -481,7 +481,7 @@
      *
      * Maintaining API and serialization compatibility with previous
      * versions of this class introduces several oddities. Mainly: We
-     * leave untouched but unused constructor arguments refering to
+     * leave untouched but unused constructor arguments referring to
      * concurrencyLevel. We accept a loadFactor constructor argument,
      * but apply it only to initial table capacity (which is the only
      * time that we can guarantee to honor it.) We also declare an
--- a/jdk/src/java.base/share/classes/java/util/concurrent/ConcurrentSkipListMap.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/concurrent/ConcurrentSkipListMap.java	Wed Jul 05 20:35:10 2017 +0200
@@ -2710,7 +2710,7 @@
         }
 
         /**
-         * Returns lowest absolute key (ignoring directonality).
+         * Returns lowest absolute key (ignoring directionality).
          */
         K lowestKey() {
             Comparator<? super K> cmp = m.comparator;
@@ -2722,7 +2722,7 @@
         }
 
         /**
-         * Returns highest absolute key (ignoring directonality).
+         * Returns highest absolute key (ignoring directionality).
          */
         K highestKey() {
             Comparator<? super K> cmp = m.comparator;
--- a/jdk/src/java.base/share/classes/java/util/concurrent/ForkJoinPool.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/java/util/concurrent/ForkJoinPool.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1328,13 +1328,16 @@
     /**
      * Number of times to spin-wait before blocking. The spins (in
      * awaitRunStateLock and awaitWork) currently use randomized
-     * spins. If/when MWAIT-like intrinsics becomes available, they
-     * may allow quieter spinning. The value of SPINS must be a power
-     * of two, at least 4. The current value causes spinning for a
-     * small fraction of typical context-switch times, well worthwhile
-     * given the typical likelihoods that blocking is not necessary.
+     * spins. Currently set to zero to reduce CPU usage.
+     *
+     * If greater than zero the value of SPINS must be a power
+     * of two, at least 4.  A value of 2048 causes spinning for a
+     * small fraction of typical context-switch times.
+     *
+     * If/when MWAIT-like intrinsics becomes available, they
+     * may allow quieter spinning.
      */
-    private static final int SPINS  = 1 << 11;
+    private static final int SPINS  = 0;
 
     /**
      * Increment for seed generators. See class ThreadLocal for
--- a/jdk/src/java.base/share/classes/javax/crypto/interfaces/package.html	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/javax/crypto/interfaces/package.html	Wed Jul 05 20:35:10 2017 +0200
@@ -47,8 +47,7 @@
 <ul>
   <li><a href=
     "{@docRoot}/../technotes/guides/security/crypto/HowToImplAProvider.html">
-    <b>How to Implement a Provider for the
-    Java<FONT SIZE=-2><SUP>TM</SUP></FONT> Cryptography Architecture
+    <b>How to Implement a Provider for the Java&trade; Cryptography Architecture
     </b></a></li>
 </ul>
 
@@ -66,8 +65,7 @@
   <li>
     <a href=
       "{@docRoot}/../technotes/guides/security/crypto/CryptoSpec.html">
-      <b>Java<FONT SIZE=-2><SUP>TM</SUP></FONT>
-      Cryptography Architecture API Specification and Reference
+      <b>Java&trade; Cryptography Architecture API Specification and Reference
       </b></a></li>
 </ul>
 
--- a/jdk/src/java.base/share/classes/javax/crypto/spec/package.html	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/javax/crypto/spec/package.html	Wed Jul 05 20:35:10 2017 +0200
@@ -62,14 +62,13 @@
   <li>
     <a href=
       "{@docRoot}/../technotes/guides/security/crypto/CryptoSpec.html">
-      <b>Java<FONT SIZE=-2><SUP>TM</SUP></FONT>
-      Cryptography Architecture API Specification and Reference
+      <b>Java&trade; Cryptography Architecture API Specification and Reference
       </b></a></li>
   <li>
     <a href=
       "{@docRoot}/../technotes/guides/security/crypto/HowToImplAProvider.html">
       <b>How to Implement a Provider for the
-      Java<FONT SIZE=-2><SUP>TM</SUP></FONT> Cryptography Architecture
+      Java&trade; Cryptography Architecture
       </b></a></li>
 </ul>
 
--- a/jdk/src/java.base/share/classes/javax/net/ssl/package.html	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/javax/net/ssl/package.html	Wed Jul 05 20:35:10 2017 +0200
@@ -38,8 +38,7 @@
 
 <ul>
   <li><a href="{@docRoot}/../technotes/guides/security/StandardNames.html">
-    <b>Java<FONT SIZE=-2><SUP>TM</SUP></FONT>
-    Cryptography Architecture Standard Algorithm Name
+    <b>Java&trade; Cryptography Architecture Standard Algorithm Name
     Documentation</b></a></li>
 </ul>
 
--- a/jdk/src/java.base/share/classes/jdk/internal/util/xml/impl/Parser.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/jdk/internal/util/xml/impl/Parser.java	Wed Jul 05 20:35:10 2017 +0200
@@ -145,12 +145,12 @@
     /**
      * ASCII character type array.
      *
-     * This array maps an ASCII (7 bit) character to the character type.<br />
-     * Possible character type values are:<br /> - ' ' for any kind of white
-     * space character;<br /> - 'a' for any lower case alphabetical character
-     * value;<br /> - 'A' for any upper case alphabetical character value;<br />
-     * - 'd' for any decimal digit character value;<br /> - 'z' for any
-     * character less then ' ' except '\t', '\n', '\r';<br /> An ASCII (7 bit)
+     * This array maps an ASCII (7 bit) character to the character type.<br>
+     * Possible character type values are:<br> - ' ' for any kind of white
+     * space character;<br> - 'a' for any lower case alphabetical character
+     * value;<br> - 'A' for any upper case alphabetical character value;<br>
+     * - 'd' for any decimal digit character value;<br> - 'z' for any
+     * character less than ' ' except '\t', '\n', '\r';<br> An ASCII (7 bit)
      * character which does not fall in any category listed above is mapped to
      * it self.
      */
@@ -158,11 +158,11 @@
     /**
      * NMTOKEN character type array.
      *
-     * This array maps an ASCII (7 bit) character to the character type.<br />
-     * Possible character type values are:<br /> - 0 for underscore ('_') or any
-     * lower and upper case alphabetical character value;<br /> - 1 for colon
-     * (':') character;<br /> - 2 for dash ('-') and dot ('.') or any decimal
-     * digit character value;<br /> - 3 for any kind of white space character<br
+     * This array maps an ASCII (7 bit) character to the character type.<br>
+     * Possible character type values are:<br> - 0 for underscore ('_') or any
+     * lower and upper case alphabetical character value;<br> - 1 for colon
+     * (':') character;<br> - 2 for dash ('-') and dot ('.') or any decimal
+     * digit character value;<br> - 3 for any kind of white space character<br
      * /> An ASCII (7 bit) character which does not fall in any category listed
      * above is mapped to 0xff.
      */
@@ -1841,10 +1841,12 @@
     /**
      * Reads an attribute value.
      *
-     * The grammar which this method can read is:<br />
-     * <code>eqstr := S &quot;=&quot; qstr</code><br />
-     * <code>qstr  := S (&quot;'&quot; string &quot;'&quot;) |
-     *  ('&quot;' string '&quot;')</code><br /> This method resolves entities
+     * The grammar this method can read is:
+     * <pre>{@code
+     * eqstr := S "=" qstr
+     * qstr  := S ("'" string "'") | ('"' string '"')
+     * }</pre>
+     * This method resolves entities
      * inside a string unless the parser parses DTD.
      *
      * @param flag The '=' character forces the method to accept the '='
@@ -2633,7 +2635,7 @@
      * Reports characters and empties the parser's buffer. This method is called
      * only if parser is going to return control to the main loop. This means
      * that this method may use parser buffer to report white space without
-     * copeing characters to temporary buffer.
+     * copying characters to temporary buffer.
      */
     protected abstract void bflash()
             throws Exception;
@@ -2642,7 +2644,7 @@
      * Reports white space characters and empties the parser's buffer. This
      * method is called only if parser is going to return control to the main
      * loop. This means that this method may use parser buffer to report white
-     * space without copeing characters to temporary buffer.
+     * space without copying characters to temporary buffer.
      */
     protected abstract void bflash_ws()
             throws Exception;
@@ -3290,16 +3292,20 @@
     }
 
     /**
-     * Maps a character to it's type.
+     * Maps a character to its type.
      *
-     * Possible character type values are:<br /> - ' ' for any kind of white
-     * space character;<br /> - 'a' for any lower case alphabetical character
-     * value;<br /> - 'A' for any upper case alphabetical character value;<br />
-     * - 'd' for any decimal digit character value;<br /> - 'z' for any
-     * character less then ' ' except '\t', '\n', '\r';<br /> - 'X' for any not
-     * ASCII character;<br /> - 'Z' for EOS character.<br /> An ASCII (7 bit)
-     * character which does not fall in any category listed above is mapped to
-     * it self.
+     * Possible character type values are:
+     * <ul>
+     * <li>' ' - for any kind of whitespace character;</li>
+     * <li>'a' - for any lower case alphabetical character value;</li>
+     * <li>'A' - for any upper case alphabetical character value;</li>
+     * <li>'d' - for any decimal digit character value;</li>
+     * <li>'z' - for any character less than ' ' except '\t', '\n', '\r';</li>
+     * <li>'X' - for any not ASCII character;</li>
+     * <li>'Z' - for EOS character.</li>
+     * </ul>
+     * An ASCII (7 bit) character which does not fall in any category
+     * listed above is mapped to itself.
      *
      * @param ch The character to map.
      * @return The type of character.
--- a/jdk/src/java.base/share/classes/jdk/internal/util/xml/impl/ParserSAX.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/jdk/internal/util/xml/impl/ParserSAX.java	Wed Jul 05 20:35:10 2017 +0200
@@ -649,7 +649,7 @@
      * Reports characters and empties the parser's buffer. This method is called
      * only if parser is going to return control to the main loop. This means
      * that this method may use parser buffer to report white space without
-     * copeing characters to temporary buffer.
+     * copying characters to temporary buffer.
      */
     protected void bflash() throws SAXException {
         if (mBuffIdx >= 0) {
@@ -663,7 +663,7 @@
      * Reports white space characters and empties the parser's buffer. This
      * method is called only if parser is going to return control to the main
      * loop. This means that this method may use parser buffer to report white
-     * space without copeing characters to temporary buffer.
+     * space without copying characters to temporary buffer.
      */
     protected void bflash_ws() throws SAXException {
         if (mBuffIdx >= 0) {
--- a/jdk/src/java.base/share/classes/sun/misc/Cache.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/Cache.java	Wed Jul 05 20:35:10 2017 +0200
@@ -196,8 +196,8 @@
     /**
      * Gets the object associated with the specified key in the Cache.
      * @param key the key in the hash table
-     * @returns the element for the key or null if the key
-     *          is not defined in the hash table.
+     * @return the element for the key or null if the key
+     *         is not defined in the hash table.
      * @see Cache#put
      */
     public synchronized Object get(Object key) {
--- a/jdk/src/java.base/share/classes/sun/misc/CharacterDecoder.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/CharacterDecoder.java	Wed Jul 05 20:35:10 2017 +0200
@@ -120,7 +120,7 @@
     /**
      * This method does an actual decode. It takes the decoded bytes and
      * writes them to the OutputStream. The integer <i>l</i> tells the
-     * method how many bytes are required. This is always <= bytesPerAtom().
+     * method how many bytes are required. This is always {@literal <=} bytesPerAtom().
      */
     protected void decodeAtom(PushbackInputStream aStream, OutputStream bStream, int l) throws IOException {
         throw new CEStreamExhausted();
--- a/jdk/src/java.base/share/classes/sun/misc/CharacterEncoder.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/CharacterEncoder.java	Wed Jul 05 20:35:10 2017 +0200
@@ -68,7 +68,7 @@
  * referenced in the See Also list below.
  *
  * @author      Chuck McManis
- * @see         CharacterDecoder;
+ * @see         CharacterDecoder
  * @see         UCEncoder
  * @see         UUEncoder
  * @see         BASE64Encoder
@@ -107,7 +107,7 @@
 
     /**
      * Encode the suffix that ends every output line. By default
-     * this method just prints a <newline> into the output stream.
+     * this method just prints a newline into the output stream.
      */
     protected void encodeLineSuffix(OutputStream aStream) throws IOException {
         pStream.println();
--- a/jdk/src/java.base/share/classes/sun/misc/ConditionLock.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/ConditionLock.java	Wed Jul 05 20:35:10 2017 +0200
@@ -34,7 +34,7 @@
  * with the lock() and unlock() methods. However if there is a thread
  * waiting for the state variable to become a particular value and you
  * simply call Unlock(), that thread will not be able to acquire the
- * lock until the state variable equals its desired value. <p>
+ * lock until the state variable equals its desired value.
  *
  * @author      Peter King
  */
--- a/jdk/src/java.base/share/classes/sun/misc/ExtensionDependency.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/ExtensionDependency.java	Wed Jul 05 20:35:10 2017 +0200
@@ -45,26 +45,26 @@
 import sun.net.www.ParseUtil;
 
 /**
- * <p>
  * This class checks dependent extensions a particular jar file may have
  * declared through its manifest attributes.
- * </p>
+ * <p>
  * Jar file declared dependent extensions through the extension-list
  * attribute. The extension-list contains a list of keys used to
  * fetch the other attributes describing the required extension.
  * If key is the extension key declared in the extension-list
  * attribute, the following describing attribute can be found in
- * the manifest :
- * key-Extension-Name:  (Specification package name)
- * key-Specification-Version: (Specification-Version)
- * key-Implementation-Version: (Implementation-Version)
- * key-Implementation-Vendor-Id: (Imlementation-Vendor-Id)
- * key-Implementation-Version: (Implementation version)
- * key-Implementation-URL: (URL to download the requested extension)
+ * the manifest:
+ * <ul>
+ * <li>key-Extension-Name:  (Specification package name)</li>
+ * <li>key-Specification-Version: (Specification-Version)</li>
+ * <li>key-Implementation-Version: (Implementation-Version)</li>
+ * <li>key-Implementation-Vendor-Id: (Imlementation-Vendor-Id)</li>
+ * <li>key-Implementation-Version: (Implementation version)</li>
+ * <li>key-Implementation-URL: (URL to download the requested extension)</li>
+ * </ul>
  * <p>
  * This class also maintain versioning consistency of installed
  * extensions dependencies declared in jar file manifest.
- * </p>
  *
  * @deprecated this class will be removed in a future release.
  * @author  Jerome Dochez
@@ -76,10 +76,9 @@
     private static Vector<ExtensionInstallationProvider> providers;
 
     /**
-     * <p>
      * Register an ExtensionInstallationProvider. The provider is responsible
      * for handling the installation (upgrade) of any missing extensions.
-     * </p>
+     *
      * @param eip ExtensionInstallationProvider implementation
      */
     public synchronized static void addExtensionInstallationProvider
@@ -92,9 +91,7 @@
     }
 
     /**
-     * <p>
      * Unregister a previously installed installation provider
-     * </p>
      */
     public synchronized static void removeExtensionInstallationProvider
         (ExtensionInstallationProvider eip)
@@ -103,10 +100,9 @@
     }
 
     /**
-     * <p>
      * Checks the dependencies of the jar file on installed extension.
-     * </p>
-     * @param jarFile containing the attriutes declaring the dependencies
+     *
+     * @param jar containing the attributes declaring the dependencies
      */
     public static boolean checkExtensionsDependencies(JarFile jar)
     {
@@ -182,9 +178,8 @@
 
 
     /*
-     * <p>
      * Check that a particular dependency on an extension is satisfied.
-     * </p>
+     *
      * @param extensionName is the key used for the attributes in the manifest
      * @param attr is the attributes of the manifest file
      *
@@ -204,10 +199,9 @@
     }
 
     /*
-     * <p>
      * Check if a particular extension is part of the currently installed
      * extensions.
-     * </p>
+     *
      * @param extensionName is the key for the attributes in the manifest
      * @param attr is the attributes of the manifest
      *
@@ -262,11 +256,9 @@
     }
 
     /*
-     * <p>
      * Check if the requested extension described by the attributes
      * in the manifest under the key extensionName is compatible with
      * the jar file.
-     * </p>
      *
      * @param extensionName key in the attribute list
      * @param attr manifest file attributes
@@ -337,10 +329,8 @@
     }
 
     /*
-     * <p>
      * An required extension is missing, if an ExtensionInstallationProvider is
      * registered, delegate the installation of that particular extension to it.
-     * </p>
      *
      * @param reqInfo Missing extension information
      * @param instInfo Older installed version information
@@ -380,11 +370,9 @@
     }
 
     /**
-     * <p>
      * Checks if the extension, that is specified in the extension-list in
      * the applet jar manifest, is already installed (i.e. exists in the
      * extension directory).
-     * </p>
      *
      * @param extensionName extension name in the extension-list
      *
@@ -428,9 +416,7 @@
     }
 
     /**
-     * <p>
      * @return the java.ext.dirs property as a list of directory
-     * </p>
      */
     private static File[] getExtDirs() {
         String s = java.security.AccessController.doPrivileged(
@@ -456,9 +442,8 @@
     }
 
     /*
-     * <p>
      * Scan the directories and return all files installed in those
-     * </p>
+     *
      * @param dirs list of directories to scan
      *
      * @return the list of files installed in all the directories
@@ -483,9 +468,7 @@
     }
 
     /*
-     * <p>
      * @return the list of installed extensions jar files
-     * </p>
      */
     private File[] getInstalledExtensions() throws IOException {
         return AccessController.doPrivileged(
@@ -503,9 +486,7 @@
     }
 
     /*
-     * <p>
      * Add the newly installed jar file to the extension class loader.
-     * </p>
      *
      * @param cl the current installed extension class loader
      *
--- a/jdk/src/java.base/share/classes/sun/misc/ExtensionInfo.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/ExtensionInfo.java	Wed Jul 05 20:35:10 2017 +0200
@@ -45,9 +45,7 @@
 public class ExtensionInfo {
 
     /**
-     * <p>
      * public static values returned by the isCompatible method
-     * </p>
      */
     public static final int COMPATIBLE = 0;
     public static final int REQUIRE_SPECIFICATION_UPGRADE = 1;
@@ -56,10 +54,8 @@
     public static final int INCOMPATIBLE = 4;
 
     /**
-     * <p>
      * attributes fully describer an extension. The underlying described
      * extension may be installed and requested.
-     * <p>
      */
     public String title;
     public String name;
@@ -76,15 +72,12 @@
 
 
     /**
-     * <p>
      * Create a new uninitialized extension information object
-     * </p>
      */
     public ExtensionInfo() {
     }
 
     /**
-     * <p>
      * Create and initialize an extension information object.
      * The initialization uses the attributes passed as being
      * the content of a manifest file to load the extension
@@ -93,7 +86,7 @@
      * extension they may depend on, the extension key parameter
      * is prepanded to the attribute name to make the key used
      * to retrieve the attribute from the manifest file
-     * <p>
+     *
      * @param extensionKey unique extension key in the manifest
      * @param attr Attributes of a manifest file
      */
@@ -149,13 +142,11 @@
     }
 
     /**
-     * <p>
      * @return true if the extension described by this extension information
      * is compatible with the extension described by the extension
      * information passed as a parameter
-     * </p>
      *
-     * @param the requested extension information to compare to
+     * @param ei the requested extension information to compare to
      */
     public int isCompatibleWith(ExtensionInfo ei) {
 
@@ -204,10 +195,8 @@
     }
 
     /**
-     * <p>
      * helper method to print sensible information on the undelying described
      * extension
-     * </p>
      */
     public String toString() {
         return "Extension : title(" + title + "), name(" + name + "), spec vendor(" +
@@ -217,15 +206,15 @@
     }
 
     /*
-     * <p>
      * helper method to compare two versions.
      * version are in the x.y.z.t pattern.
-     * </p>
+     *
      * @param source version to compare to
      * @param target version used to compare against
-     * @return < 0 if source < version
-     *         > 0 if source > version
-     *         = 0 if source = version
+     * @return <pre>{@code
+     *   < 0 if source < version
+     *   > 0 if source > version
+     *   = 0 if source = version}</pre>
      */
     private int compareExtensionVersion(String source, String target)
         throws NumberFormatException
@@ -238,15 +227,15 @@
 
 
     /*
-     * <p>
      * helper method to compare two versions.
      * version are in the x.y.z.t pattern.
-     * </p>
+     *
      * @param source version to compare to
      * @param target version used to compare against
-     * @return < 0 if source < version
-     *         > 0 if source > version
-     *         = 0 if source = version
+     * @return <pre>{@code
+     *   < 0 if source < version
+     *   > 0 if source > version
+     *   = 0 if source = version}</pre>
      */
     private int strictCompareExtensionVersion(String source, String target)
         throws NumberFormatException
--- a/jdk/src/java.base/share/classes/sun/misc/FDBigInteger.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/FDBigInteger.java	Wed Jul 05 20:35:10 2017 +0200
@@ -384,8 +384,8 @@
      * Retrieves the normalization bias of the <code>FDBigIntger</code>. The
      * normalization bias is a left shift such that after it the highest word
      * of the value will have the 4 highest bits equal to zero:
-     * <code>(highestWord & 0xf0000000) == 0</code>, but the next bit should be 1
-     * <code>(highestWord & 0x08000000) != 0</code>.
+     * {@code (highestWord & 0xf0000000) == 0}, but the next bit should be 1
+     * {@code (highestWord & 0x08000000) != 0}.
      *
      * @return The normalization bias.
      */
@@ -546,9 +546,9 @@
      * We assume that S has been normalized, as above, and that
      * "this" has been left-shifted accordingly.
      * Also assumed, of course, is that the result, q, can be expressed
-     * as an integer, 0 <= q < 10.
+     * as an integer, {@code 0 <= q < 10}.
      *
-     * @param The divisor of this <code>FDBigInteger</code>.
+     * @param S The divisor of this <code>FDBigInteger</code>.
      * @return <code>q = (int)(this / S)</code>.
      */
     /*@
@@ -685,7 +685,7 @@
      *
      * @param p5 The exponent of the power-of-five factor.
      * @param p2 The exponent of the power-of-two factor.
-     * @return
+     * @return The multiplication result.
      */
     /*@
      @ requires this.value() == 0 || p5 == 0 && p2 == 0;
@@ -931,11 +931,11 @@
     /**
      * Compares the parameter with this <code>FDBigInteger</code>. Returns an
      * integer accordingly as:
-     * <pre>
-     * >0: this > other
-     *  0: this == other
-     * <0: this < other
-     * </pre>
+     * <pre>{@code
+     * > 0: this > other
+     *   0: this == other
+     * < 0: this < other
+     * }</pre>
      *
      * @param other The <code>FDBigInteger</code> to compare.
      * @return A negative value, zero, or a positive value according to the
@@ -974,11 +974,11 @@
      * Compares this <code>FDBigInteger</code> with
      * <code>5<sup>p5</sup> * 2<sup>p2</sup></code>.
      * Returns an integer accordingly as:
-     * <pre>
-     * >0: this > other
-     *  0: this == other
-     * <0: this < other
-     * </pre>
+     * <pre>{@code
+     * > 0: this > other
+     *   0: this == other
+     * < 0: this < other
+     * }</pre>
      * @param p5 The exponent of the power-of-five factor.
      * @param p2 The exponent of the power-of-two factor.
      * @return A negative value, zero, or a positive value according to the
@@ -1011,11 +1011,11 @@
     /**
      * Compares this <code>FDBigInteger</code> with <code>x + y</code>. Returns a
      * value according to the comparison as:
-     * <pre>
+     * <pre>{@code
      * -1: this <  x + y
      *  0: this == x + y
      *  1: this >  x + y
-     * </pre>
+     * }</pre>
      * @param x The first addend of the sum to compare.
      * @param y The second addend of the sum to compare.
      * @return -1, 0, or 1 according to the result of the comparison.
--- a/jdk/src/java.base/share/classes/sun/misc/FloatingDecimal.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/FloatingDecimal.java	Wed Jul 05 20:35:10 2017 +0200
@@ -154,7 +154,7 @@
 
         /**
          * Indicates the sign of the value.
-         * @return <code>value < 0.0</code>.
+         * @return {@code value < 0.0}.
          */
         public boolean isNegative();
 
--- a/jdk/src/java.base/share/classes/sun/misc/IOUtils.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/IOUtils.java	Wed Jul 05 20:35:10 2017 +0200
@@ -39,7 +39,7 @@
     /**
      * Read up to <code>length</code> of bytes from <code>in</code>
      * until EOF is detected.
-     * @param in input stream, must not be null
+     * @param is input stream, must not be null
      * @param length number of bytes to read, -1 or Integer.MAX_VALUE means
      *        read as much as possible
      * @param readAll if true, an EOFException will be thrown if not enough
--- a/jdk/src/java.base/share/classes/sun/misc/JarFilter.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/JarFilter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,10 +29,8 @@
 import java.io.FilenameFilter;
 
 /**
- * <p>
  * This class checks that only jar and zip files are included in the file list.
  * This class is used in extension installation support (ExtensionDependency).
- * <p>
  *
  * @deprecated this class will be removed in a future release.
  * @author  Michael Colburn
--- a/jdk/src/java.base/share/classes/sun/misc/JavaLangAccess.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/JavaLangAccess.java	Wed Jul 05 20:35:10 2017 +0200
@@ -91,14 +91,14 @@
      * may be added to the delete on exit list by the application shutdown
      * hooks.
      *
-     * @params slot  the slot in the shutdown hook array, whose element
-     *               will be invoked in order during shutdown
-     * @params registerShutdownInProgress true to allow the hook
-     *               to be registered even if the shutdown is in progress.
-     * @params hook  the hook to be registered
+     * @param slot  the slot in the shutdown hook array, whose element
+     *              will be invoked in order during shutdown
+     * @param registerShutdownInProgress true to allow the hook
+     *        to be registered even if the shutdown is in progress.
+     * @param hook  the hook to be registered
      *
-     * @throw IllegalStateException if shutdown is in progress and
-     *          the slot is not valid to register.
+     * @throws IllegalStateException if shutdown is in progress and
+     *         the slot is not valid to register.
      */
     void registerShutdownHook(int slot, boolean registerShutdownInProgress, Runnable hook);
 
--- a/jdk/src/java.base/share/classes/sun/misc/Perf.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/Perf.java	Wed Jul 05 20:35:10 2017 +0200
@@ -67,13 +67,13 @@
      * <code>AccessController.doPrivileged(PrivilegedAction)</code>.
      * <p> Here is a suggested idiom for use of this class:
      *
-     * <blockquote><pre>
+     * <blockquote><pre>{@code
      * class MyTrustedClass {
      *   private static final Perf perf =
      *       AccessController.doPrivileged(new Perf.GetPerfAction<Perf>());
      *   ...
      * }
-     * </pre></blockquote>
+     * }</pre></blockquote>
      * <p>
      * In the presence of a security manager, the <code>MyTrustedClass</code>
      * class in the above example will need to be granted the
@@ -171,8 +171,7 @@
      * The attach mode specifies the access permissions requested for the
      * instrumentation buffer of the target virtual machine. The permitted
      * access permissions are:
-     * <p>
-     * <bl>
+     * <ul>
      * <li>"r"  - Read only access. This Java virtual machine has only
      * read access to the instrumentation buffer for the target Java
      * virtual machine.
@@ -180,7 +179,7 @@
      * write access to the instrumentation buffer for the target Java virtual
      * machine. This mode is currently not supported and is reserved for
      * future enhancements.
-     * </bl>
+     * </ul>
      *
      * @param   lvmid            an integer that uniquely identifies the
      *                           target local Java virtual machine.
--- a/jdk/src/java.base/share/classes/sun/misc/PerfCounter.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/PerfCounter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -37,7 +37,7 @@
  * The perf counters will be created in the jvmstat perf buffer
  * that the HotSpot VM creates. The default size is 32K and thus
  * the number of counters is bounded.  You can alter the size
- * with -XX:PerfDataMemorySize=<bytes> option. If there is
+ * with {@code -XX:PerfDataMemorySize=<bytes>} option. If there is
  * insufficient memory in the jvmstat perf buffer, the C heap memory
  * will be used and thus the application will continue to run if
  * the counters added exceeds the buffer size but the counters
--- a/jdk/src/java.base/share/classes/sun/misc/PerformanceLogger.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/PerformanceLogger.java	Wed Jul 05 20:35:10 2017 +0200
@@ -51,10 +51,12 @@
  * <P>
  * To automatically track startup performance in an app or applet,
  * use the command-line parameter sun.perflog as follows:<BR>
+ * <pre>{@code
  *     -Dsun.perflog[=file:<filename>]
+ * }</pre>
  * <BR>
  * where simply using the parameter with no value will enable output
- * to the console and a value of "file:<filename>" will cause
+ * to the console and a value of "{@code file:<filename>}" will cause
  * that given filename to be created and used for all output.
  * <P>
  * By default, times are measured using System.currentTimeMillis().  To use
--- a/jdk/src/java.base/share/classes/sun/misc/Resource.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/Resource.java	Wed Jul 05 20:35:10 2017 +0200
@@ -154,7 +154,8 @@
 
     /**
      * Returns the Resource data as a ByteBuffer, but only if the input stream
-     * was implemented on top of a ByteBuffer. Return <tt>null</tt> otherwise.
+     * was implemented on top of a ByteBuffer. Return {@code null} otherwise.
+     * @return Resource data or null.
      */
     public ByteBuffer getByteBuffer() throws IOException {
         InputStream in = cachedInputStream();
--- a/jdk/src/java.base/share/classes/sun/misc/Signal.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/Signal.java	Wed Jul 05 20:35:10 2017 +0200
@@ -50,7 +50,7 @@
  * Signal objects are created based on their names. For example:
  * <blockquote><pre>
  * new Signal("INT");
- * </blockquote></pre>
+ * </pre></blockquote>
  * constructs a signal object corresponding to <code>SIGINT</code>, which is
  * typically produced when the user presses <code>Ctrl-C</code> at the command line.
  * The <code>Signal</code> constructor throws <code>IllegalArgumentException</code>
@@ -64,7 +64,7 @@
  *     }
  * };
  * Signal.handle(new Signal("INT"), handler);
- * </blockquote></pre>
+ * </pre></blockquote>
  *
  * @author   Sheng Liang
  * @author   Bill Shannon
@@ -149,7 +149,7 @@
      *
      * @param sig a signal
      * @param handler the handler to be registered with the given signal.
-     * @result the old handler
+     * @return the old handler
      * @exception IllegalArgumentException the signal is in use by the VM
      * @see sun.misc.Signal#raise(Signal sig)
      * @see sun.misc.SignalHandler
--- a/jdk/src/java.base/share/classes/sun/misc/Unsafe.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/Unsafe.java	Wed Jul 05 20:35:10 2017 +0200
@@ -641,9 +641,9 @@
      * <li>String: any object (not just a java.lang.String)
      * <li>InterfaceMethodRef: (NYI) a method handle to invoke on that call site's arguments
      * </ul>
-     * @params hostClass context for linkage, access control, protection domain, and class loader
-     * @params data      bytes of a class file
-     * @params cpPatches where non-null entries exist, they replace corresponding CP entries in data
+     * @param hostClass context for linkage, access control, protection domain, and class loader
+     * @param data      bytes of a class file
+     * @param cpPatches where non-null entries exist, they replace corresponding CP entries in data
      */
     public native Class<?> defineAnonymousClass(Class<?> hostClass, byte[] data, Object[] cpPatches);
 
@@ -808,9 +808,9 @@
      * The system imposes a maximum of 3 samples, representing
      * averages over the last 1,  5,  and  15 minutes, respectively.
      *
-     * @params loadavg an array of double of size nelems
-     * @params nelems the number of samples to be retrieved and
-     *         must be 1 to 3.
+     * @param loadavg an array of double of size nelems
+     * @param nelems the number of samples to be retrieved and
+     *        must be 1 to 3.
      *
      * @return the number of samples actually retrieved; or -1
      *         if the load average is unobtainable.
@@ -1108,7 +1108,6 @@
      * <p>
      * 8-byte atomicity is only guaranteed on platforms on which
      * support atomic accesses to longs.
-     * <p>
      *
      * @param o Java heap object in which the value resides, if any, else
      *        null
--- a/jdk/src/java.base/share/classes/sun/misc/VM.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/VM.java	Wed Jul 05 20:35:10 2017 +0200
@@ -315,7 +315,7 @@
     }
 
     /*
-     * Add <tt>n</tt> to the objects pending for finalization count.
+     * Add {@code n} to the objects pending for finalization count.
      *
      * @param n an integer value to be added to the objects pending
      * for finalization count
--- a/jdk/src/java.base/share/classes/sun/misc/resources/Messages.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/resources/Messages.java	Wed Jul 05 20:35:10 2017 +0200
@@ -26,7 +26,7 @@
 package sun.misc.resources;
 
 /**
- * <p> This class represents the <code>ResourceBundle</code>
+ * This class represents the {@code ResourceBundle}
  * for sun.misc.
  *
  * @author Michael Colburn
@@ -35,9 +35,9 @@
 public class Messages extends java.util.ListResourceBundle {
 
     /**
-     * Returns the contents of this <code>ResourceBundle</code>.
-     * <p>
-     * @return the contents of this <code>ResourceBundle</code>.
+     * Returns the contents of this {@code ResourceBundle}.
+     *
+     * @return the contents of this {@code ResourceBundle}.
      */
     public Object[][] getContents() {
         return contents;
--- a/jdk/src/java.base/share/classes/sun/misc/resources/Messages_de.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/resources/Messages_de.java	Wed Jul 05 20:35:10 2017 +0200
@@ -26,7 +26,7 @@
 package sun.misc.resources;
 
 /**
- * <p> This class represents the <code>ResourceBundle</code>
+ * This class represents the {@code ResourceBundle}
  * for sun.misc.
  *
  * @author Michael Colburn
@@ -35,9 +35,9 @@
 public class Messages_de extends java.util.ListResourceBundle {
 
     /**
-     * Returns the contents of this <code>ResourceBundle</code>.
-     * <p>
-     * @return the contents of this <code>ResourceBundle</code>.
+     * Returns the contents of this {@code ResourceBundle}.
+     *
+     * @return the contents of this {@code ResourceBundle}.
      */
     public Object[][] getContents() {
         return contents;
--- a/jdk/src/java.base/share/classes/sun/misc/resources/Messages_es.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/resources/Messages_es.java	Wed Jul 05 20:35:10 2017 +0200
@@ -26,7 +26,7 @@
 package sun.misc.resources;
 
 /**
- * <p> This class represents the <code>ResourceBundle</code>
+ * This class represents the {@code ResourceBundle}
  * for sun.misc.
  *
  * @author Michael Colburn
@@ -35,9 +35,9 @@
 public class Messages_es extends java.util.ListResourceBundle {
 
     /**
-     * Returns the contents of this <code>ResourceBundle</code>.
-     * <p>
-     * @return the contents of this <code>ResourceBundle</code>.
+     * Returns the contents of this {@code ResourceBundle}.
+     *
+     * @return the contents of this {@code ResourceBundle}.
      */
     public Object[][] getContents() {
         return contents;
--- a/jdk/src/java.base/share/classes/sun/misc/resources/Messages_fr.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/resources/Messages_fr.java	Wed Jul 05 20:35:10 2017 +0200
@@ -26,7 +26,7 @@
 package sun.misc.resources;
 
 /**
- * <p> This class represents the <code>ResourceBundle</code>
+ * This class represents the {@code ResourceBundle}
  * for sun.misc.
  *
  * @author Michael Colburn
@@ -35,9 +35,9 @@
 public class Messages_fr extends java.util.ListResourceBundle {
 
     /**
-     * Returns the contents of this <code>ResourceBundle</code>.
-     * <p>
-     * @return the contents of this <code>ResourceBundle</code>.
+     * Returns the contents of this {@code ResourceBundle}.
+     *
+     * @return the contents of this {@code ResourceBundle}.
      */
     public Object[][] getContents() {
         return contents;
--- a/jdk/src/java.base/share/classes/sun/misc/resources/Messages_it.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/resources/Messages_it.java	Wed Jul 05 20:35:10 2017 +0200
@@ -26,7 +26,7 @@
 package sun.misc.resources;
 
 /**
- * <p> This class represents the <code>ResourceBundle</code>
+ * This class represents the {@code ResourceBundle}
  * for sun.misc.
  *
  * @author Michael Colburn
@@ -35,9 +35,9 @@
 public class Messages_it extends java.util.ListResourceBundle {
 
     /**
-     * Returns the contents of this <code>ResourceBundle</code>.
-     * <p>
-     * @return the contents of this <code>ResourceBundle</code>.
+     * Returns the contents of this {@code ResourceBundle}.
+     *
+     * @return the contents of this {@code ResourceBundle}.
      */
     public Object[][] getContents() {
         return contents;
--- a/jdk/src/java.base/share/classes/sun/misc/resources/Messages_ja.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/resources/Messages_ja.java	Wed Jul 05 20:35:10 2017 +0200
@@ -26,7 +26,7 @@
 package sun.misc.resources;
 
 /**
- * <p> This class represents the <code>ResourceBundle</code>
+ * This class represents the {@code ResourceBundle}
  * for sun.misc.
  *
  * @author Michael Colburn
@@ -35,9 +35,9 @@
 public class Messages_ja extends java.util.ListResourceBundle {
 
     /**
-     * Returns the contents of this <code>ResourceBundle</code>.
-     * <p>
-     * @return the contents of this <code>ResourceBundle</code>.
+     * Returns the contents of this {@code ResourceBundle}.
+     *
+     * @return the contents of this {@code ResourceBundle}.
      */
     public Object[][] getContents() {
         return contents;
--- a/jdk/src/java.base/share/classes/sun/misc/resources/Messages_ko.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/resources/Messages_ko.java	Wed Jul 05 20:35:10 2017 +0200
@@ -26,7 +26,7 @@
 package sun.misc.resources;
 
 /**
- * <p> This class represents the <code>ResourceBundle</code>
+ * This class represents the {@code ResourceBundle}
  * for sun.misc.
  *
  * @author Michael Colburn
@@ -35,9 +35,9 @@
 public class Messages_ko extends java.util.ListResourceBundle {
 
     /**
-     * Returns the contents of this <code>ResourceBundle</code>.
-     * <p>
-     * @return the contents of this <code>ResourceBundle</code>.
+     * Returns the contents of this {@code ResourceBundle}.
+     *
+     * @return the contents of this {@code ResourceBundle}.
      */
     public Object[][] getContents() {
         return contents;
--- a/jdk/src/java.base/share/classes/sun/misc/resources/Messages_pt_BR.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/resources/Messages_pt_BR.java	Wed Jul 05 20:35:10 2017 +0200
@@ -26,7 +26,7 @@
 package sun.misc.resources;
 
 /**
- * <p> This class represents the <code>ResourceBundle</code>
+ * This class represents the {@code ResourceBundle}
  * for sun.misc.
  *
  * @author Michael Colburn
@@ -35,9 +35,9 @@
 public class Messages_pt_BR extends java.util.ListResourceBundle {
 
     /**
-     * Returns the contents of this <code>ResourceBundle</code>.
-     * <p>
-     * @return the contents of this <code>ResourceBundle</code>.
+     * Returns the contents of this {@code ResourceBundle}.
+     *
+     * @return the contents of this {@code ResourceBundle}.
      */
     public Object[][] getContents() {
         return contents;
--- a/jdk/src/java.base/share/classes/sun/misc/resources/Messages_sv.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/resources/Messages_sv.java	Wed Jul 05 20:35:10 2017 +0200
@@ -26,7 +26,7 @@
 package sun.misc.resources;
 
 /**
- * <p> This class represents the <code>ResourceBundle</code>
+ * This class represents the {@code ResourceBundle}
  * for sun.misc.
  *
  * @author Michael Colburn
@@ -35,9 +35,9 @@
 public class Messages_sv extends java.util.ListResourceBundle {
 
     /**
-     * Returns the contents of this <code>ResourceBundle</code>.
-     * <p>
-     * @return the contents of this <code>ResourceBundle</code>.
+     * Returns the contents of this {@code ResourceBundle}.
+     *
+     * @return the contents of this {@code ResourceBundle}.
      */
     public Object[][] getContents() {
         return contents;
--- a/jdk/src/java.base/share/classes/sun/misc/resources/Messages_zh_CN.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/resources/Messages_zh_CN.java	Wed Jul 05 20:35:10 2017 +0200
@@ -26,7 +26,7 @@
 package sun.misc.resources;
 
 /**
- * <p> This class represents the <code>ResourceBundle</code>
+ * This class represents the {@code ResourceBundle}
  * for sun.misc.
  *
  * @author Michael Colburn
@@ -35,9 +35,9 @@
 public class Messages_zh_CN extends java.util.ListResourceBundle {
 
     /**
-     * Returns the contents of this <code>ResourceBundle</code>.
-     * <p>
-     * @return the contents of this <code>ResourceBundle</code>.
+     * Returns the contents of this {@code ResourceBundle}.
+     *
+     * @return the contents of this {@code ResourceBundle}.
      */
     public Object[][] getContents() {
         return contents;
--- a/jdk/src/java.base/share/classes/sun/misc/resources/Messages_zh_TW.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/misc/resources/Messages_zh_TW.java	Wed Jul 05 20:35:10 2017 +0200
@@ -26,7 +26,7 @@
 package sun.misc.resources;
 
 /**
- * <p> This class represents the <code>ResourceBundle</code>
+ * This class represents the {@code ResourceBundle}
  * for sun.misc.
  *
  * @author Michael Colburn
@@ -35,9 +35,9 @@
 public class Messages_zh_TW extends java.util.ListResourceBundle {
 
     /**
-     * Returns the contents of this <code>ResourceBundle</code>.
-     * <p>
-     * @return the contents of this <code>ResourceBundle</code>.
+     * Returns the contents of this {@code ResourceBundle}.
+     *
+     * @return the contents of this {@code ResourceBundle}.
      */
     public Object[][] getContents() {
         return contents;
--- a/jdk/src/java.base/share/classes/sun/net/www/protocol/http/HttpURLConnection.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/net/www/protocol/http/HttpURLConnection.java	Wed Jul 05 20:35:10 2017 +0200
@@ -983,7 +983,7 @@
         SocketPermission p = URLtoSocketPermission(this.url);
         if (p != null) {
             try {
-                AccessController.doPrivileged(
+                AccessController.doPrivilegedWithCombiner(
                     new PrivilegedExceptionAction<>() {
                         public Void run() throws IOException {
                             plainConnect0();
@@ -1244,7 +1244,7 @@
 
         if (p != null) {
             try {
-                return AccessController.doPrivileged(
+                return AccessController.doPrivilegedWithCombiner(
                     new PrivilegedExceptionAction<>() {
                         public OutputStream run() throws IOException {
                             return getOutputStream0();
@@ -1422,7 +1422,7 @@
 
         if (p != null) {
             try {
-                return AccessController.doPrivileged(
+                return AccessController.doPrivilegedWithCombiner(
                     new PrivilegedExceptionAction<>() {
                         public InputStream run() throws IOException {
                             return getInputStream0();
@@ -2565,7 +2565,7 @@
 
         if (p != null) {
             try {
-                return AccessController.doPrivileged(
+                return AccessController.doPrivilegedWithCombiner(
                     new PrivilegedExceptionAction<>() {
                         public Boolean run() throws IOException {
                             return followRedirect0(loc, stat, locUrl0);
--- a/jdk/src/java.base/share/classes/sun/nio/cs/HKSCS.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/nio/cs/HKSCS.java	Wed Jul 05 20:35:10 2017 +0200
@@ -378,7 +378,6 @@
                             dst[dp++] = repl[1];
                         continue;
                     }
-                    sp++;
                 }
                 if (bb > MAX_SINGLEBYTE) {        // DoubleByte
                     dst[dp++] = (byte)(bb >> 8);
--- a/jdk/src/java.base/share/classes/sun/nio/cs/Surrogate.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/nio/cs/Surrogate.java	Wed Jul 05 20:35:10 2017 +0200
@@ -175,10 +175,10 @@
          * @param  in   The source buffer, from which one more character
          *              will be consumed if c is a high surrogate
          *
-         * @returns  Either a parsed UCS-4 character, in which case the isPair()
-         *           and increment() methods will return meaningful values, or
-         *           -1, in which case error() will return a descriptive result
-         *           object
+         * @return  Either a parsed UCS-4 character, in which case the isPair()
+         *          and increment() methods will return meaningful values, or
+         *          -1, in which case error() will return a descriptive result
+         *          object
          */
         public int parse(char c, CharBuffer in) {
             if (Character.isHighSurrogate(c)) {
@@ -216,10 +216,10 @@
          * @param  ip   The input index
          * @param  il   The input limit
          *
-         * @returns  Either a parsed UCS-4 character, in which case the isPair()
-         *           and increment() methods will return meaningful values, or
-         *           -1, in which case error() will return a descriptive result
-         *           object
+         * @return  Either a parsed UCS-4 character, in which case the isPair()
+         *          and increment() methods will return meaningful values, or
+         *          -1, in which case error() will return a descriptive result
+         *          object
          */
         public int parse(char c, char[] ia, int ip, int il) {
             assert (ia[ip] == c);
@@ -280,9 +280,9 @@
          * @param  dst  The destination buffer, to which one or two UTF-16
          *              characters will be written
          *
-         * @returns  Either a positive count of the number of UTF-16 characters
-         *           written to the destination buffer, or -1, in which case
-         *           error() will return a descriptive result object
+         * @return  Either a positive count of the number of UTF-16 characters
+         *          written to the destination buffer, or -1, in which case
+         *          error() will return a descriptive result object
          */
         public int generate(int uc, int len, CharBuffer dst) {
             if (Character.isBmpCodePoint(uc)) {
@@ -325,9 +325,9 @@
          * @param  dp   The destination position
          * @param  dl   The destination limit
          *
-         * @returns  Either a positive count of the number of UTF-16 characters
-         *           written to the destination buffer, or -1, in which case
-         *           error() will return a descriptive result object
+         * @return  Either a positive count of the number of UTF-16 characters
+         *          written to the destination buffer, or -1, in which case
+         *          error() will return a descriptive result object
          */
         public int generate(int uc, int len, char[] da, int dp, int dl) {
             if (Character.isBmpCodePoint(uc)) {
--- a/jdk/src/java.base/share/classes/sun/security/x509/AVA.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/AVA.java	Wed Jul 05 20:35:10 2017 +0200
@@ -454,7 +454,7 @@
             if (embeddedHex.size() > 0) {
                 // add space(s) before embedded hex bytes
                 for (int i = 0; i < spaceCount; i++) {
-                    temp.append(" ");
+                    temp.append(' ');
                 }
                 spaceCount = 0;
 
@@ -472,7 +472,7 @@
             } else {
                 // add space(s)
                 for (int i = 0; i < spaceCount; i++) {
-                    temp.append(" ");
+                    temp.append(' ');
                 }
                 spaceCount = 0;
                 temp.append((char)c);
@@ -853,7 +853,7 @@
                 }
                 sbuffer.append(c);
             }
-            typeAndValue.append(sbuffer.toString());
+            typeAndValue.append(sbuffer);
         }
         return typeAndValue.toString();
     }
@@ -1039,7 +1039,7 @@
         StringBuilder   retval = new StringBuilder(40);
 
         retval.append(keyword);
-        retval.append("=");
+        retval.append('=');
 
         try {
             String valStr = value.getAsString();
@@ -1147,9 +1147,11 @@
                 // Emit the string ... quote it if needed
                 // if string is already quoted, don't re-quote
                 if (!alreadyQuoted && quoteNeeded) {
-                    retval.append("\"" + sbuffer.toString() + "\"");
+                    retval.append('\"')
+                        .append(sbuffer)
+                        .append('\"');
                 } else {
-                    retval.append(sbuffer.toString());
+                    retval.append(sbuffer);
                 }
             }
         } catch (IOException e) {
--- a/jdk/src/java.base/share/classes/sun/security/x509/AuthorityKeyIdentifierExtension.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/AuthorityKeyIdentifierExtension.java	Wed Jul 05 20:35:10 2017 +0200
@@ -196,17 +196,20 @@
      * Return the object as a string.
      */
     public String toString() {
-        String s = super.toString() + "AuthorityKeyIdentifier [\n";
+        StringBuilder sb = new StringBuilder();
+        sb.append(super.toString())
+            .append("AuthorityKeyIdentifier [\n");
         if (id != null) {
-            s += id.toString();     // id already has a newline
+            sb.append(id);       // id already has a newline
         }
         if (names != null) {
-            s += names.toString() + "\n";
+            sb.append(names).append('\n');
         }
         if (serialNum != null) {
-            s += serialNum.toString() + "\n";
+            sb.append(serialNum).append('\n');
         }
-        return (s + "]\n");
+        sb.append("]\n");
+        return sb.toString();
     }
 
     /**
--- a/jdk/src/java.base/share/classes/sun/security/x509/BasicConstraintsExtension.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/BasicConstraintsExtension.java	Wed Jul 05 20:35:10 2017 +0200
@@ -171,15 +171,11 @@
       * Return user readable form of extension.
       */
      public String toString() {
-         String s = super.toString() + "BasicConstraints:[\n";
-
-         s += ((ca) ? ("  CA:true") : ("  CA:false")) + "\n";
-         if (pathLen >= 0) {
-             s += "  PathLen:" + pathLen + "\n";
-         } else {
-             s += "  PathLen: undefined\n";
-         }
-         return (s + "]\n");
+         return super.toString() +
+             "BasicConstraints:[\n  CA:" + ca +
+             "\n  PathLen:" +
+             ((pathLen >= 0) ? String.valueOf(pathLen) : " undefined") +
+             "\n]\n";
      }
 
      /**
--- a/jdk/src/java.base/share/classes/sun/security/x509/CRLDistributionPointsExtension.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/CRLDistributionPointsExtension.java	Wed Jul 05 20:35:10 2017 +0200
@@ -231,8 +231,8 @@
             distributionPoints = (List<DistributionPoint>)obj;
         } else {
             throw new IOException("Attribute name [" + name +
-                                "] not recognized by " +
-                                "CertAttrSet:" + extensionName + ".");
+                                  "] not recognized by " +
+                                  "CertAttrSet:" + extensionName + '.');
         }
         encodeThis();
     }
@@ -245,8 +245,8 @@
             return distributionPoints;
         } else {
             throw new IOException("Attribute name [" + name +
-                                "] not recognized by " +
-                                "CertAttrSet:" + extensionName + ".");
+                                  "] not recognized by " +
+                                  "CertAttrSet:" + extensionName + '.');
         }
     }
 
--- a/jdk/src/java.base/share/classes/sun/security/x509/CRLNumberExtension.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/CRLNumberExtension.java	Wed Jul 05 20:35:10 2017 +0200
@@ -146,8 +146,8 @@
             }
             crlNumber = (BigInteger)obj;
         } else {
-          throw new IOException("Attribute name not recognized by"
-                                + " CertAttrSet:" + extensionName + ".");
+            throw new IOException("Attribute name not recognized by" +
+                                  " CertAttrSet:" + extensionName + '.');
         }
         encodeThis();
     }
@@ -172,8 +172,8 @@
         if (name.equalsIgnoreCase(NUMBER)) {
             crlNumber = null;
         } else {
-          throw new IOException("Attribute name not recognized by"
-                                + " CertAttrSet:" + extensionName + ".");
+            throw new IOException("Attribute name not recognized by" +
+                                  " CertAttrSet:" + extensionName + '.');
         }
         encodeThis();
     }
@@ -182,10 +182,15 @@
      * Returns a printable representation of the CRLNumberExtension.
      */
     public String toString() {
-        String s = super.toString() + extensionLabel + ": " +
-                   ((crlNumber == null) ? "" : Debug.toHexString(crlNumber))
-                   + "\n";
-        return (s);
+        StringBuilder sb = new StringBuilder();
+        sb.append(super.toString())
+            .append(extensionLabel)
+            .append(": ");
+        if (crlNumber != null) {
+            sb.append(Debug.toHexString(crlNumber));
+        }
+        sb.append('\n');
+        return sb.toString();
     }
 
     /**
@@ -195,7 +200,7 @@
      * @exception IOException on encoding errors.
      */
     public void encode(OutputStream out) throws IOException {
-       DerOutputStream  tmp = new DerOutputStream();
+        DerOutputStream tmp = new DerOutputStream();
         encode(out, PKIXExtensions.CRLNumber_Id, true);
     }
 
--- a/jdk/src/java.base/share/classes/sun/security/x509/CertException.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/CertException.java	Wed Jul 05 20:35:10 2017 +0200
@@ -158,7 +158,7 @@
      */
     public String toString()
     {
-        return "[Certificate Exception: " + getMessage() + "]";
+        return "[Certificate Exception: " + getMessage() + ']';
     }
 
     /**
@@ -168,6 +168,6 @@
     {
         return getVerfDescription()
                 + ( (moreData != null)
-                    ? ( "\n  (" + moreData + ")" ) : "" );
+                    ? ( "\n  (" + moreData + ')' ) : "" );
     }
 }
--- a/jdk/src/java.base/share/classes/sun/security/x509/CertificatePoliciesExtension.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/CertificatePoliciesExtension.java	Wed Jul 05 20:35:10 2017 +0200
@@ -160,10 +160,12 @@
         if (certPolicies == null) {
             return "";
         }
-        StringBuilder sb = new StringBuilder(super.toString());
-        sb.append("CertificatePolicies [\n");
+
+        StringBuilder sb = new StringBuilder();
+        sb.append(super.toString())
+            .append("CertificatePolicies [\n");
         for (PolicyInformation info : certPolicies) {
-            sb.append(info.toString());
+            sb.append(info);
         }
         sb.append("]\n");
         return sb.toString();
--- a/jdk/src/java.base/share/classes/sun/security/x509/CertificateValidity.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/CertificateValidity.java	Wed Jul 05 20:35:10 2017 +0200
@@ -134,8 +134,8 @@
     public String toString() {
         if (notBefore == null || notAfter == null)
             return "";
-        return ("Validity: [From: " + notBefore.toString() +
-             ",\n               To: " + notAfter.toString() + "]");
+        return "Validity: [From: " + notBefore +
+               ",\n               To: " + notAfter + ']';
     }
 
     /**
--- a/jdk/src/java.base/share/classes/sun/security/x509/DistributionPoint.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/DistributionPoint.java	Wed Jul 05 20:35:10 2017 +0200
@@ -380,23 +380,29 @@
      */
     public String toString() {
         StringBuilder sb = new StringBuilder();
+        sb.append("DistributionPoint:\n     ");
         if (fullName != null) {
-            sb.append("DistributionPoint:\n     " + fullName + "\n");
+            sb.append(fullName);
         }
         if (relativeName != null) {
-            sb.append("DistributionPoint:\n     " + relativeName + "\n");
+            sb.append(relativeName);
         }
+        sb.append('\n');
 
         if (reasonFlags != null) {
             sb.append("   ReasonFlags:\n");
             for (int i = 0; i < reasonFlags.length; i++) {
                 if (reasonFlags[i]) {
-                    sb.append("    " + reasonToString(i) + "\n");
+                    sb.append("    ")
+                        .append(reasonToString(i))
+                        .append('\n');
                 }
             }
         }
         if (crlIssuer != null) {
-            sb.append("   CRLIssuer:" + crlIssuer + "\n");
+            sb.append("   CRLIssuer:")
+                .append(crlIssuer)
+                .append('\n');
         }
         return sb.toString();
     }
--- a/jdk/src/java.base/share/classes/sun/security/x509/DistributionPointName.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/DistributionPointName.java	Wed Jul 05 20:35:10 2017 +0200
@@ -230,13 +230,13 @@
      */
     public String toString() {
         StringBuilder sb = new StringBuilder();
+        sb.append("DistributionPointName:\n     ");
         if (fullName != null) {
-            sb.append("DistributionPointName:\n     " + fullName + "\n");
-
+            sb.append(fullName);
         } else {
-            sb.append("DistributionPointName:\n     " + relativeName + "\n");
+            sb.append(relativeName);
         }
-
+        sb.append('\n');
         return sb.toString();
     }
 }
--- a/jdk/src/java.base/share/classes/sun/security/x509/EDIPartyName.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/EDIPartyName.java	Wed Jul 05 20:35:10 2017 +0200
@@ -209,10 +209,15 @@
      * Return the printable string.
      */
     public String toString() {
-        return ("EDIPartyName: " +
-                 ((assigner == null) ? "" :
-                   ("  nameAssigner = " + assigner + ","))
-                 + "  partyName = " + party);
+        StringBuilder sb = new StringBuilder("EDIPartyName: ");
+        if (assigner != null) {
+            sb.append("  nameAssigner = ")
+              .append(assigner)
+              .append(',');
+        }
+        sb.append("  partyName = ")
+          .append(party);
+        return sb.toString();
     }
 
     /**
--- a/jdk/src/java.base/share/classes/sun/security/x509/Extension.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/Extension.java	Wed Jul 05 20:35:10 2017 +0200
@@ -219,13 +219,8 @@
      * Returns the Extension in user readable form.
      */
     public String toString() {
-        String s = "ObjectId: " + extensionId.toString();
-        if (critical) {
-            s += " Criticality=true\n";
-        } else {
-            s += " Criticality=false\n";
-        }
-        return (s);
+        return "ObjectId: " + extensionId +
+                " Criticality=" + critical + '\n';
     }
 
     // Value to mix up the hash
--- a/jdk/src/java.base/share/classes/sun/security/x509/GeneralSubtree.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/GeneralSubtree.java	Wed Jul 05 20:35:10 2017 +0200
@@ -127,15 +127,22 @@
      * Return a printable string of the GeneralSubtree.
      */
     public String toString() {
-        String s = "\n   GeneralSubtree: [\n" +
-            "    GeneralName: " + ((name == null) ? "" : name.toString()) +
-            "\n    Minimum: " + minimum;
-            if (maximum == -1) {
-                s += "\t    Maximum: undefined";
-            } else
-                s += "\t    Maximum: " + maximum;
-            s += "    ]\n";
-        return (s);
+        StringBuilder sb = new StringBuilder();
+        sb.append("\n   GeneralSubtree: [")
+            .append("\n    GeneralName: ");
+        if (name != null) {
+            sb.append(name);
+        }
+        sb.append("\n    Minimum: ")
+            .append(minimum)
+            .append("\n    Maximum: ");
+        if (maximum == -1) {
+            sb.append("undefined");
+        } else {
+            sb.append(maximum);
+        }
+        sb.append("    ]\n");
+        return sb.toString();
     }
 
     /**
--- a/jdk/src/java.base/share/classes/sun/security/x509/GeneralSubtrees.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/GeneralSubtrees.java	Wed Jul 05 20:35:10 2017 +0200
@@ -124,8 +124,7 @@
      * Return a printable string of the GeneralSubtree.
      */
     public String toString() {
-        String s = "   GeneralSubtrees:\n" + trees.toString() + "\n";
-        return s;
+        return "   GeneralSubtrees:\n" + trees + '\n';
     }
 
     /**
--- a/jdk/src/java.base/share/classes/sun/security/x509/IPAddressName.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/IPAddressName.java	Wed Jul 05 20:35:10 2017 +0200
@@ -263,7 +263,7 @@
             if (address.length == 8) {
                 byte[] mask = new byte[4];
                 System.arraycopy(address, 4, mask, 0, 4);
-                name = name + "/" +
+                name = name + '/' +
                        InetAddress.getByAddress(mask).getHostAddress();
             }
         } else {
@@ -285,7 +285,7 @@
                     if (!ba.get(i))
                         break;
                 }
-                name = name + "/" + i;
+                name = name + '/' + i;
                 // Verify remaining bits 0
                 for (; i < 16*8; i++) {
                     if (ba.get(i)) {
--- a/jdk/src/java.base/share/classes/sun/security/x509/IssuerAlternativeNameExtension.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/IssuerAlternativeNameExtension.java	Wed Jul 05 20:35:10 2017 +0200
@@ -140,17 +140,20 @@
      * Returns a printable representation of the IssuerAlternativeName.
      */
     public String toString() {
-
-        String result = super.toString() + "IssuerAlternativeName [\n";
-        if(names == null) {
-            result += "  null\n";
+        StringBuilder sb = new StringBuilder();
+        sb.append(super.toString())
+            .append("IssuerAlternativeName [\n");
+        if (names == null) {
+            sb.append("  null\n");
         } else {
-            for(GeneralName name: names.names()) {
-                result += "  "+name+"\n";
+            for (GeneralName name : names.names()) {
+                sb.append("  ")
+                    .append(name)
+                    .append('\n');
             }
         }
-        result += "]\n";
-        return result;
+        sb.append("]\n");
+        return sb.toString();
     }
 
     /**
--- a/jdk/src/java.base/share/classes/sun/security/x509/IssuingDistributionPointExtension.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/IssuingDistributionPointExtension.java	Wed Jul 05 20:35:10 2017 +0200
@@ -441,9 +441,9 @@
      * Returns the extension as user readable string.
      */
     public String toString() {
-
-        StringBuilder sb = new StringBuilder(super.toString());
-        sb.append("IssuingDistributionPoint [\n  ");
+        StringBuilder sb = new StringBuilder();
+        sb.append(super.toString())
+            .append("IssuingDistributionPoint [\n  ");
 
         if (distributionPoint != null) {
             sb.append(distributionPoint);
@@ -453,23 +453,18 @@
             sb.append(revocationReasons);
         }
 
-        sb.append((hasOnlyUserCerts)
-                ? ("  Only contains user certs: true")
-                : ("  Only contains user certs: false")).append("\n");
-
-        sb.append((hasOnlyCACerts)
-                ? ("  Only contains CA certs: true")
-                : ("  Only contains CA certs: false")).append("\n");
-
-        sb.append((hasOnlyAttributeCerts)
-                ? ("  Only contains attribute certs: true")
-                : ("  Only contains attribute certs: false")).append("\n");
-
-        sb.append((isIndirectCRL)
-                ? ("  Indirect CRL: true")
-                : ("  Indirect CRL: false")).append("\n");
-
-        sb.append("]\n");
+        sb.append("  Only contains user certs: ")
+            .append(hasOnlyUserCerts)
+            .append('\n')
+            .append("  Only contains CA certs: ")
+            .append(hasOnlyCACerts)
+            .append('\n')
+            .append("  Only contains attribute certs: ")
+            .append(hasOnlyAttributeCerts)
+            .append('\n')
+            .append("  Indirect CRL: ")
+            .append(isIndirectCRL)
+            .append("\n]\n");
 
         return sb.toString();
     }
--- a/jdk/src/java.base/share/classes/sun/security/x509/NameConstraintsExtension.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/NameConstraintsExtension.java	Wed Jul 05 20:35:10 2017 +0200
@@ -214,12 +214,19 @@
      * Return the printable string.
      */
     public String toString() {
-        return (super.toString() + "NameConstraints: [" +
-                ((permitted == null) ? "" :
-                     ("\n    Permitted:" + permitted.toString())) +
-                ((excluded == null) ? "" :
-                     ("\n    Excluded:" + excluded.toString()))
-                + "   ]\n");
+        StringBuilder sb = new StringBuilder();
+        sb.append(super.toString())
+            .append("NameConstraints: [");
+        if (permitted != null) {
+            sb.append("\n    Permitted:")
+                .append(permitted);
+        }
+        if (excluded != null) {
+            sb.append("\n    Excluded:")
+                .append(excluded);
+        }
+        sb.append("   ]\n");
+        return sb.toString();
     }
 
     /**
--- a/jdk/src/java.base/share/classes/sun/security/x509/PolicyConstraintsExtension.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/PolicyConstraintsExtension.java	Wed Jul 05 20:35:10 2017 +0200
@@ -175,19 +175,24 @@
      * Return the extension as user readable string.
      */
     public String toString() {
-        String s;
-        s = super.toString() + "PolicyConstraints: [" + "  Require: ";
-        if (require == -1)
-            s += "unspecified;";
-        else
-            s += require + ";";
-        s += "\tInhibit: ";
-        if (inhibit == -1)
-            s += "unspecified";
-        else
-            s += inhibit;
-        s += " ]\n";
-        return s;
+        StringBuilder sb = new StringBuilder();
+        sb.append(super.toString())
+            .append("PolicyConstraints: [")
+            .append("  Require: ");
+        if (require == -1) {
+            sb.append("unspecified;");
+        } else {
+            sb.append(require)
+                .append(';');
+        }
+        sb.append("\tInhibit: ");
+        if (inhibit == -1) {
+            sb.append("unspecified");
+        } else {
+            sb.append(inhibit);
+        }
+        sb.append(" ]\n");
+        return sb.toString();
     }
 
     /**
--- a/jdk/src/java.base/share/classes/sun/security/x509/PolicyInformation.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/PolicyInformation.java	Wed Jul 05 20:35:10 2017 +0200
@@ -258,9 +258,7 @@
      * Return a printable representation of the PolicyInformation.
      */
     public String toString() {
-        StringBuilder s = new StringBuilder("  [" + policyIdentifier.toString());
-        s.append(policyQualifiers + "  ]\n");
-        return s.toString();
+        return "  [" + policyIdentifier + policyQualifiers + "  ]\n";
     }
 
     /**
--- a/jdk/src/java.base/share/classes/sun/security/x509/PrivateKeyUsageExtension.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/PrivateKeyUsageExtension.java	Wed Jul 05 20:35:10 2017 +0200
@@ -175,11 +175,22 @@
      * Return the printable string.
      */
     public String toString() {
-        return(super.toString() +
-                "PrivateKeyUsage: [\n" +
-                ((notBefore == null) ? "" : "From: " + notBefore.toString() + ", ")
-                + ((notAfter == null) ? "" : "To: " + notAfter.toString())
-                + "]\n");
+        StringBuilder sb = new StringBuilder();
+        sb.append(super.toString())
+            .append("PrivateKeyUsage: [\n");
+        if (notBefore != null) {
+            sb.append("From: ")
+                .append(notBefore);
+            if (notAfter != null) {
+                sb.append(", ");
+            }
+        }
+        if (notAfter != null) {
+            sb.append("To: ")
+                .append(notAfter);
+        }
+        sb.append("]\n");
+        return sb.toString();
     }
 
     /**
--- a/jdk/src/java.base/share/classes/sun/security/x509/RDN.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/RDN.java	Wed Jul 05 20:35:10 2017 +0200
@@ -348,14 +348,11 @@
             return assertion[0].toString();
         }
 
-        StringBuilder sb = new StringBuilder();
+        StringJoiner sj = new StringJoiner(" + ");
         for (int i = 0; i < assertion.length; i++) {
-            if (i != 0) {
-                sb.append(" + ");
-            }
-            sb.append(assertion[i].toString());
+            sj.add(assertion[i].toString());
         }
-        return sb.toString();
+        return sj.toString();
     }
 
     /*
@@ -376,14 +373,11 @@
             return assertion[0].toRFC1779String(oidMap);
         }
 
-        StringBuilder sb = new StringBuilder();
+        StringJoiner sj = new StringJoiner(" + ");
         for (int i = 0; i < assertion.length; i++) {
-            if (i != 0) {
-                sb.append(" + ");
-            }
-            sb.append(assertion[i].toRFC1779String(oidMap));
+            sj.add(assertion[i].toRFC1779String(oidMap));
         }
-        return sb.toString();
+        return sj.toString();
     }
 
     /*
--- a/jdk/src/java.base/share/classes/sun/security/x509/SerialNumber.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/SerialNumber.java	Wed Jul 05 20:35:10 2017 +0200
@@ -101,7 +101,7 @@
      * Return the SerialNumber as user readable string.
      */
     public String toString() {
-        return ("SerialNumber: [" + Debug.toHexString(serialNum) + "]");
+        return "SerialNumber: [" + Debug.toHexString(serialNum) + ']';
     }
 
     /**
--- a/jdk/src/java.base/share/classes/sun/security/x509/SubjectInfoAccessExtension.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/SubjectInfoAccessExtension.java	Wed Jul 05 20:35:10 2017 +0200
@@ -238,8 +238,8 @@
      * Return the extension as user readable string.
      */
     public String toString() {
-        return super.toString() + "SubjectInfoAccess [\n  "
-               + accessDescriptions + "\n]\n";
+        return super.toString() +
+            "SubjectInfoAccess [\n  " + accessDescriptions + "\n]\n";
     }
 
 }
--- a/jdk/src/java.base/share/classes/sun/security/x509/SubjectKeyIdentifierExtension.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/SubjectKeyIdentifierExtension.java	Wed Jul 05 20:35:10 2017 +0200
@@ -115,8 +115,8 @@
      * Returns a printable representation.
      */
     public String toString() {
-        return super.toString() + "SubjectKeyIdentifier [\n"
-                + String.valueOf(id) + "]\n";
+        return super.toString() +
+            "SubjectKeyIdentifier [\n" + id + "]\n";
     }
 
     /**
--- a/jdk/src/java.base/share/classes/sun/security/x509/X500Name.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/X500Name.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,6 +31,7 @@
 import java.security.AccessController;
 import java.security.Principal;
 import java.util.*;
+import java.util.StringJoiner;
 
 import sun.security.util.*;
 import javax.security.auth.x500.X500Principal;
@@ -689,14 +690,11 @@
          * The encodings of adjoining RelativeDistinguishedNames are separated
          * by a comma character (',' ASCII 44).
          */
-        StringBuilder fullname = new StringBuilder(48);
+        StringJoiner sj = new StringJoiner(",");
         for (int i = names.length - 1; i >= 0; i--) {
-            if (i < names.length - 1) {
-                fullname.append(',');
-            }
-            fullname.append(names[i].toRFC2253String(oidMap));
+            sj.add(names[i].toRFC2253String(oidMap));
         }
-        return fullname.toString();
+        return sj.toString();
     }
 
     public String getRFC2253CanonicalName() {
@@ -722,14 +720,11 @@
          * The encodings of adjoining RelativeDistinguishedNames are separated
          * by a comma character (',' ASCII 44).
          */
-        StringBuilder fullname = new StringBuilder(48);
+        StringJoiner sj = new StringJoiner(",");
         for (int i = names.length - 1; i >= 0; i--) {
-            if (i < names.length - 1) {
-                fullname.append(',');
-            }
-            fullname.append(names[i].toRFC2253String(true));
+            sj.add(names[i].toRFC2253String(true));
         }
-        canonicalDn = fullname.toString();
+        canonicalDn = sj.toString();
         return canonicalDn;
     }
 
@@ -1064,16 +1059,16 @@
             return;
         }
 
-        StringBuilder sb = new StringBuilder(48);
-        if (names != null) {
-            for (int i = names.length - 1; i >= 0; i--) {
-                if (i != names.length - 1) {
-                    sb.append(", ");
-                }
-                sb.append(names[i].toString());
-            }
+        if (names == null) {
+            dn = "";
+            return;
         }
-        dn = sb.toString();
+
+        StringJoiner sj = new StringJoiner(", ");
+        for (int i = names.length - 1; i >= 0; i--) {
+            sj.add(names[i].toString());
+        }
+        dn = sj.toString();
     }
 
     /*
@@ -1090,16 +1085,15 @@
             return names[0].toRFC1779String(oidMap);
         }
 
-        StringBuilder sb = new StringBuilder(48);
-        if (names != null) {
-            for (int i = names.length - 1; i >= 0; i--) {
-                if (i != names.length - 1) {
-                    sb.append(", ");
-                }
-                sb.append(names[i].toRFC1779String(oidMap));
-            }
+        if (names == null) {
+            return "";
         }
-        return sb.toString();
+
+        StringJoiner sj = new StringJoiner(", ");
+        for (int i = names.length - 1; i >= 0; i--) {
+            sj.add(names[i].toRFC1779String(oidMap));
+        }
+        return sj.toString();
     }
 
     /****************************************************************/
--- a/jdk/src/java.base/share/classes/sun/security/x509/X509CRLEntryImpl.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/X509CRLEntryImpl.java	Wed Jul 05 20:35:10 2017 +0200
@@ -291,40 +291,47 @@
     public String toString() {
         StringBuilder sb = new StringBuilder();
 
-        sb.append(serialNumber.toString());
-        sb.append("  On: " + revocationDate.toString());
+        sb.append(serialNumber)
+            .append("  On: ")
+            .append(revocationDate);
         if (certIssuer != null) {
-            sb.append("\n    Certificate issuer: " + certIssuer);
+            sb.append("\n    Certificate issuer: ")
+                .append(certIssuer);
         }
         if (extensions != null) {
             Collection<Extension> allEntryExts = extensions.getAllExtensions();
             Extension[] exts = allEntryExts.toArray(new Extension[0]);
 
-            sb.append("\n    CRL Entry Extensions: " + exts.length);
+            sb.append("\n    CRL Entry Extensions: ")
+                .append(exts.length);
             for (int i = 0; i < exts.length; i++) {
-                sb.append("\n    [" + (i+1) + "]: ");
+                sb.append("\n    [")
+                    .append(i+1)
+                    .append("]: ");
                 Extension ext = exts[i];
                 try {
                     if (OIDMap.getClass(ext.getExtensionId()) == null) {
-                        sb.append(ext.toString());
+                        sb.append(ext);
                         byte[] extValue = ext.getExtensionValue();
                         if (extValue != null) {
                             DerOutputStream out = new DerOutputStream();
                             out.putOctetString(extValue);
                             extValue = out.toByteArray();
                             HexDumpEncoder enc = new HexDumpEncoder();
-                            sb.append("Extension unknown: "
-                                      + "DER encoded OCTET string =\n"
-                                      + enc.encodeBuffer(extValue) + "\n");
+                            sb.append("Extension unknown: ")
+                                .append("DER encoded OCTET string =\n")
+                                .append(enc.encodeBuffer(extValue))
+                                .append('\n');
                         }
-                    } else
-                        sb.append(ext.toString()); //sub-class exists
+                    } else {
+                        sb.append(ext); //sub-class exists
+                    }
                 } catch (Exception e) {
                     sb.append(", Error parsing this extension");
                 }
             }
         }
-        sb.append("\n");
+        sb.append('\n');
         return sb.toString();
     }
 
--- a/jdk/src/java.base/share/classes/sun/security/x509/X509CRLImpl.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/X509CRLImpl.java	Wed Jul 05 20:35:10 2017 +0200
@@ -537,47 +537,65 @@
      */
     public String toString() {
         StringBuilder sb = new StringBuilder();
-        sb.append("X.509 CRL v" + (version+1) + "\n");
+        sb.append("X.509 CRL v")
+            .append(version+1)
+            .append('\n');
         if (sigAlgId != null)
-            sb.append("Signature Algorithm: " + sigAlgId.toString() +
-                  ", OID=" + (sigAlgId.getOID()).toString() + "\n");
+            sb.append("Signature Algorithm: ")
+                .append(sigAlgId)
+                .append(", OID=")
+                .append(sigAlgId.getOID())
+                .append('\n');
         if (issuer != null)
-            sb.append("Issuer: " + issuer.toString() + "\n");
+            sb.append("Issuer: ")
+                .append(issuer)
+                .append('\n');
         if (thisUpdate != null)
-            sb.append("\nThis Update: " + thisUpdate.toString() + "\n");
+            sb.append("\nThis Update: ")
+                .append(thisUpdate)
+                .append('\n');
         if (nextUpdate != null)
-            sb.append("Next Update: " + nextUpdate.toString() + "\n");
+            sb.append("Next Update: ")
+                .append(nextUpdate)
+                .append('\n');
         if (revokedList.isEmpty())
             sb.append("\nNO certificates have been revoked\n");
         else {
-            sb.append("\nRevoked Certificates: " + revokedList.size());
+            sb.append("\nRevoked Certificates: ")
+                .append(revokedList.size());
             int i = 1;
             for (X509CRLEntry entry: revokedList) {
-                sb.append("\n[" + i++ + "] " + entry.toString());
+                sb.append("\n[")
+                    .append(i++)
+                    .append("] ")
+                    .append(entry);
             }
         }
         if (extensions != null) {
             Collection<Extension> allExts = extensions.getAllExtensions();
             Object[] objs = allExts.toArray();
-            sb.append("\nCRL Extensions: " + objs.length);
+            sb.append("\nCRL Extensions: ")
+                .append(objs.length);
             for (int i = 0; i < objs.length; i++) {
-                sb.append("\n[" + (i+1) + "]: ");
+                sb.append("\n[").append(i+1).append("]: ");
                 Extension ext = (Extension)objs[i];
                 try {
-                   if (OIDMap.getClass(ext.getExtensionId()) == null) {
-                       sb.append(ext.toString());
-                       byte[] extValue = ext.getExtensionValue();
-                       if (extValue != null) {
-                           DerOutputStream out = new DerOutputStream();
-                           out.putOctetString(extValue);
-                           extValue = out.toByteArray();
-                           HexDumpEncoder enc = new HexDumpEncoder();
-                           sb.append("Extension unknown: "
-                                     + "DER encoded OCTET string =\n"
-                                     + enc.encodeBuffer(extValue) + "\n");
-                      }
-                   } else
-                       sb.append(ext.toString()); // sub-class exists
+                    if (OIDMap.getClass(ext.getExtensionId()) == null) {
+                        sb.append(ext);
+                        byte[] extValue = ext.getExtensionValue();
+                        if (extValue != null) {
+                            DerOutputStream out = new DerOutputStream();
+                            out.putOctetString(extValue);
+                            extValue = out.toByteArray();
+                            HexDumpEncoder enc = new HexDumpEncoder();
+                            sb.append("Extension unknown: ")
+                                .append("DER encoded OCTET string =\n")
+                                .append(enc.encodeBuffer(extValue))
+                                .append('\n');
+                        }
+                    } else {
+                        sb.append(ext); // sub-class exists
+                    }
                 } catch (Exception e) {
                     sb.append(", Error parsing this extension");
                 }
@@ -585,10 +603,12 @@
         }
         if (signature != null) {
             HexDumpEncoder encoder = new HexDumpEncoder();
-            sb.append("\nSignature:\n" + encoder.encodeBuffer(signature)
-                      + "\n");
-        } else
+            sb.append("\nSignature:\n")
+                .append(encoder.encodeBuffer(signature))
+                .append('\n');
+        } else {
             sb.append("NOT signed yet\n");
+        }
         return sb.toString();
     }
 
--- a/jdk/src/java.base/share/classes/sun/security/x509/X509CertImpl.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/X509CertImpl.java	Wed Jul 05 20:35:10 2017 +0200
@@ -81,7 +81,7 @@
 
     private static final long serialVersionUID = -3457612960190864406L;
 
-    private static final String DOT = ".";
+    private static final char DOT = '.';
     /**
      * Public attribute names.
      */
@@ -799,17 +799,10 @@
         if (info == null || algId == null || signature == null)
             return "";
 
-        StringBuilder sb = new StringBuilder();
-
-        sb.append("[\n");
-        sb.append(info.toString() + "\n");
-        sb.append("  Algorithm: [" + algId.toString() + "]\n");
-
         HexDumpEncoder encoder = new HexDumpEncoder();
-        sb.append("  Signature:\n" + encoder.encodeBuffer(signature));
-        sb.append("\n]");
-
-        return sb.toString();
+        return "[\n" + info + '\n' +
+            "  Algorithm: [" + algId + "]\n" +
+            "  Signature:\n" + encoder.encodeBuffer(signature) + "\n]";
     }
 
     // the strongly typed gets, as per java.security.cert.X509Certificate
@@ -1941,31 +1934,30 @@
      * only contains 0-9 and A-F. No small case, no colon.
      */
     private String getCertificateFingerPrint(String mdAlg) {
-        String fingerPrint = "";
         try {
             byte[] encCertInfo = getEncoded();
             MessageDigest md = MessageDigest.getInstance(mdAlg);
             byte[] digest = md.digest(encCertInfo);
-            StringBuffer buf = new StringBuffer();
+            StringBuilder sb = new StringBuilder(digest.length * 2);
             for (int i = 0; i < digest.length; i++) {
-                byte2hex(digest[i], buf);
+                byte2hex(digest[i], sb);
             }
-            fingerPrint = buf.toString();
+            return sb.toString();
         } catch (NoSuchAlgorithmException | CertificateEncodingException e) {
             // ignored
         }
-        return fingerPrint;
+        return "";
     }
 
     /**
-     * Converts a byte to hex digit and writes to the supplied buffer
+     * Converts a byte to hex digit and writes to the supplied builder
      */
-    private static void byte2hex(byte b, StringBuffer buf) {
+    private static void byte2hex(byte b, StringBuilder buf) {
         char[] hexChars = { '0', '1', '2', '3', '4', '5', '6', '7', '8',
                 '9', 'A', 'B', 'C', 'D', 'E', 'F' };
         int high = ((b & 0xf0) >> 4);
         int low = (b & 0x0f);
-        buf.append(hexChars[high]);
-        buf.append(hexChars[low]);
+        buf.append(hexChars[high])
+            .append(hexChars[low]);
     }
 }
--- a/jdk/src/java.base/share/classes/sun/security/x509/X509CertInfo.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/security/x509/X509CertInfo.java	Wed Jul 05 20:35:10 2017 +0200
@@ -299,55 +299,60 @@
         }
         StringBuilder sb = new StringBuilder();
 
-        sb.append("[\n");
-        sb.append("  " + version.toString() + "\n");
-        sb.append("  Subject: " + subject.toString() + "\n");
-        sb.append("  Signature Algorithm: " + algId.toString() + "\n");
-        sb.append("  Key:  " + pubKey.toString() + "\n");
-        sb.append("  " + interval.toString() + "\n");
-        sb.append("  Issuer: " + issuer.toString() + "\n");
-        sb.append("  " + serialNum.toString() + "\n");
+        sb.append("[\n")
+            .append("  ").append(version).append('\n')
+            .append("  Subject: ").append(subject).append('\n')
+            .append("  Signature Algorithm: ").append(algId).append('\n')
+            .append("  Key:  ").append(pubKey).append('\n')
+            .append("  ").append(interval).append('\n')
+            .append("  Issuer: ").append(issuer).append('\n')
+            .append("  ").append(serialNum).append('\n');
 
         // optional v2, v3 extras
         if (issuerUniqueId != null) {
-            sb.append("  Issuer Id:\n" + issuerUniqueId.toString() + "\n");
+            sb.append("  Issuer Id:\n").append(issuerUniqueId).append('\n');
         }
         if (subjectUniqueId != null) {
-            sb.append("  Subject Id:\n" + subjectUniqueId.toString() + "\n");
+            sb.append("  Subject Id:\n").append(subjectUniqueId).append('\n');
         }
         if (extensions != null) {
             Collection<Extension> allExts = extensions.getAllExtensions();
             Extension[] exts = allExts.toArray(new Extension[0]);
-            sb.append("\nCertificate Extensions: " + exts.length);
+            sb.append("\nCertificate Extensions: ").append(exts.length);
             for (int i = 0; i < exts.length; i++) {
-                sb.append("\n[" + (i+1) + "]: ");
+                sb.append("\n[").append(i+1).append("]: ");
                 Extension ext = exts[i];
                 try {
                     if (OIDMap.getClass(ext.getExtensionId()) == null) {
-                        sb.append(ext.toString());
+                        sb.append(ext);
                         byte[] extValue = ext.getExtensionValue();
                         if (extValue != null) {
                             DerOutputStream out = new DerOutputStream();
                             out.putOctetString(extValue);
                             extValue = out.toByteArray();
                             HexDumpEncoder enc = new HexDumpEncoder();
-                            sb.append("Extension unknown: "
-                                      + "DER encoded OCTET string =\n"
-                                      + enc.encodeBuffer(extValue) + "\n");
+                            sb.append("Extension unknown: ")
+                                .append("DER encoded OCTET string =\n")
+                                .append(enc.encodeBuffer(extValue))
+                                .append('\n');
                         }
-                    } else
-                        sb.append(ext.toString()); //sub-class exists
+                    } else {
+                        sb.append(ext); //sub-class exists
+                    }
                 } catch (Exception e) {
                     sb.append(", Error parsing this extension");
                 }
             }
             Map<String,Extension> invalid = extensions.getUnparseableExtensions();
             if (invalid.isEmpty() == false) {
-                sb.append("\nUnparseable certificate extensions: " + invalid.size());
+                sb.append("\nUnparseable certificate extensions: ")
+                    .append(invalid.size());
                 int i = 1;
                 for (Extension ext : invalid.values()) {
-                    sb.append("\n[" + (i++) + "]: ");
-                    sb.append(ext);
+                    sb.append("\n[")
+                        .append(i++)
+                        .append("]: ")
+                        .append(ext);
                 }
             }
         }
--- a/jdk/src/java.base/share/classes/sun/text/CompactByteArray.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/CompactByteArray.java	Wed Jul 05 20:35:10 2017 +0200
@@ -49,7 +49,7 @@
  * Han ideographs have the same value.  However, lookup is much faster than a
  * hash table.
  * A compact array of any primitive data type serves two purposes:
- * <UL type = round>
+ * <UL type = circle>
  *     <LI>Fast access of the indexed values.
  *     <LI>Smaller memory footprint.
  * </UL>
--- a/jdk/src/java.base/share/classes/sun/text/ComposedCharIter.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/ComposedCharIter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -50,7 +50,7 @@
     }
 
     /**
-     * Construct a new <tt>ComposedCharIter</tt>.  The iterator will return
+     * Construct a new {@code ComposedCharIter}.  The iterator will return
      * all Unicode characters with canonical decompositions, excluding Korean
      * Hangul characters.
      */
@@ -58,10 +58,10 @@
 
     /**
      * Returns the next precomposed Unicode character.
-     * Repeated calls to <tt>next</tt> return all of the precomposed characters defined
+     * Repeated calls to {@code next} return all of the precomposed characters defined
      * by Unicode, in ascending order.  After all precomposed characters have
-     * been returned, {@link #hasNext} will return <tt>false</tt> and further calls
-     * to <tt>next</tt> will return {@link #DONE}.
+     * been returned, {@link #hasNext} will return {@code false} and further calls
+     * to {@code next} will return {@link #DONE}.
      */
     public int next() {
         if (curChar == decompNum - 1) {
--- a/jdk/src/java.base/share/classes/sun/text/Normalizer.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/Normalizer.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
  * This Normalizer is for Unicode 3.2 support for IDNA only.
  * Developers should not use this class.
  *
- * @ since 1.6
+ * @since 1.6
  */
 public final class Normalizer {
 
--- a/jdk/src/java.base/share/classes/sun/text/bidi/BidiBase.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/bidi/BidiBase.java	Wed Jul 05 20:35:10 2017 +0200
@@ -81,14 +81,13 @@
  *
  * <h3>General remarks about the API:</h3>
  *
- * The &quot;limit&quot; of a sequence of characters is the position just after
+ * The "limit" of a sequence of characters is the position just after
  * their last character, i.e., one more than that position.
  * <p>
  *
- * Some of the API methods provide access to &quot;runs&quot;. Such a
- * &quot;run&quot; is defined as a sequence of characters that are at the same
+ * Some of the API methods provide access to "runs". Such a
+ * "run" is defined as a sequence of characters that are at the same
  * embedding level after performing the Bidi algorithm.
- * <p>
  *
  * <h3>Basic concept: paragraph</h3>
  * A piece of text can be divided into several paragraphs by characters
@@ -141,7 +140,8 @@
  * these special values are designed that way. Also, the implementation
  * assumes that MAX_EXPLICIT_LEVEL is odd.
  *
- * <ul><b>See Also:</b>
+ * <p><b>See Also:</b>
+ * <ul>
  * <li>{@link #LEVEL_DEFAULT_LTR}
  * <li>{@link #LEVEL_DEFAULT_RTL}
  * <li>{@link #LEVEL_OVERRIDE}
@@ -153,7 +153,8 @@
  * Reordering mode values indicate which variant of the Bidi algorithm to
  * use.
  *
- * <ul><b>See Also:</b>
+ * <p><b>See Also:</b>
+ * <ul>
  * <li>{@link #setReorderingMode}
  * <li>{@link #REORDER_DEFAULT}
  * <li>{@link #REORDER_NUMBERS_SPECIAL}
@@ -166,7 +167,8 @@
  *
  * <h3>Basic concept: Reordering Options</h3>
  * Reordering options can be applied during Bidi text transformations.
- * <ul><b>See Also:</b>
+ * <p><b>See Also:</b>
+ * <ul>
  * <li>{@link #setReorderingOptions}
  * <li>{@link #OPTION_DEFAULT}
  * <li>{@link #OPTION_INSERT_MARKS}
@@ -202,7 +204,7 @@
  * and therefore its implementation omitted from this sample code.</li>
  * </ul>
  *
- * <pre>
+ * <pre>{@code
  *
  *  package com.ibm.icu.dev.test.bidi;
  *
@@ -451,7 +453,7 @@
  *      }
  *  }
  *
- * </pre>
+ * }</pre>
  */
 
 public class BidiBase {
@@ -2419,9 +2421,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>,
+     *        {@code paraLevel<=embeddingLevels[]<=MAX_EXPLICIT_LEVEL},
      *        with one exception: a level of zero may be specified for a
-     *        paragraph separator even if <code>paraLevel&gt;0</code> when multiple
+     *        paragraph separator even if {@code paraLevel > 0} 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;
@@ -2680,7 +2682,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.
      *
      * @param paragraph a paragraph of text with optional character and
      *        paragraph attribute information
@@ -2817,7 +2819,7 @@
     }
 
     /**
-     * Get the index of a paragraph, given a position within the text.<p>
+     * 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>.
--- a/jdk/src/java.base/share/classes/sun/text/bidi/BidiRun.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/bidi/BidiRun.java	Wed Jul 05 20:35:10 2017 +0200
@@ -42,7 +42,7 @@
 /**
  * A BidiRun represents a sequence of characters at the same embedding level.
  * The Bidi algorithm decomposes a piece of text into sequences of characters
- * at the same embedding level, each such sequence is called a <quote>run</quote>.
+ * at the same embedding level, each such sequence is called a "run".
  *
  * <p>A BidiRun represents such a run by storing its essential properties,
  * but does not duplicate the characters which form the run.
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/ICUBinary.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/ICUBinary.java	Wed Jul 05 20:35:10 2017 +0200
@@ -65,7 +65,7 @@
     /**
     * <p>ICU data header reader method.
     * Takes a ICU generated big-endian input stream, parse the ICU standard
-    * file header and authenticates them.</p>
+    * file header and authenticates them.
     * <p>Header format:
     * <ul>
     *     <li> Header size (char)
@@ -84,7 +84,7 @@
     *                             [0] major [1] minor [2] milli [3] micro
     *     <li> Unicode version (4 bytes) this ICU is based on.
     * </ul>
-    * </p>
+    *
     * <p>
     * Example of use:<br>
     * <pre>
@@ -98,7 +98,7 @@
     *    System.out.println("This is not a ICU data file");
     * }
     * </pre>
-    * </p>
+    *
     * @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.
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/IntTrie.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/IntTrie.java	Wed Jul 05 20:35:10 2017 +0200
@@ -58,7 +58,7 @@
     * 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
+    * @param datamanipulate object which provides methods to parse the char
     *                        data
     * @throws IOException thrown when data reading fails
     * @draft 2.1
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/NormalizerBase.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/NormalizerBase.java	Wed Jul 05 20:35:10 2017 +0200
@@ -55,16 +55,16 @@
  * In Unicode, this can be encoded as a single character (the
  * "composed" form):
  *
- * <p>
+ * <pre>
  *      00C1    LATIN CAPITAL LETTER A WITH ACUTE
- * </p>
+ * </pre>
  *
  * or as two separate characters (the "decomposed" form):
  *
- * <p>
+ * <pre>
  *      0041    LATIN CAPITAL LETTER A
  *      0301    COMBINING ACUTE ACCENT
- * </p>
+ * </pre>
  *
  * To a user of your program, however, both of these sequences should be
  * treated as the same "user-level" character "A with acute accent".  When you
@@ -76,17 +76,17 @@
  *
  * Similarly, the string "ffi" can be encoded as three separate letters:
  *
- * <p>
+ * <pre>
  *      0066    LATIN SMALL LETTER F
  *      0066    LATIN SMALL LETTER F
  *      0069    LATIN SMALL LETTER I
- * </p>
+ * </pre>
  *
  * or as the single character
  *
- * <p>
+ * <pre>
  *      FB03    LATIN SMALL LIGATURE FFI
- * </p>
+ * </pre>
  *
  * The ffi ligature is not a distinct semantic character, and strictly speaking
  * it shouldn't be in Unicode at all, but it was included for compatibility
@@ -555,12 +555,12 @@
     //-------------------------------------------------------------------------
 
     /**
-     * Creates a new <tt>Normalizer</tt> object for iterating over the
+     * Creates a new {@code Normalizer} object for iterating over the
      * normalized form of a given string.
      * <p>
-     * The <tt>options</tt> parameter specifies which optional
-     * <tt>Normalizer</tt> features are to be enabled for this object.
-     * <p>
+     * The {@code options} parameter specifies which optional
+     * {@code Normalizer} features are to be enabled for this object.
+     *
      * @param str  The string to be normalized.  The normalization
      *              will start at the beginning of the string.
      *
@@ -579,9 +579,9 @@
     }
 
     /**
-     * Creates a new <tt>Normalizer</tt> object for iterating over the
+     * 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.
      *
@@ -592,9 +592,9 @@
     }
 
     /**
-     * Creates a new <tt>Normalizer</tt> object for iterating over the
+     * 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.
      *
@@ -615,13 +615,13 @@
     }
 
     /**
-     * Clones this <tt>Normalizer</tt> object.  All properties of this
+     * Clones this {@code Normalizer} 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}.
      * However, the text storage underlying
-     * the <tt>CharacterIterator</tt> is not duplicated unless the
-     * iterator's <tt>clone</tt> method does so.
+     * the {@code CharacterIterator} is not duplicated unless the
+     * iterator's {@code clone} method does so.
      * @stable ICU 2.8
      */
     public Object clone() {
@@ -791,7 +791,7 @@
     //-------------------------------------------------------------------------
 
     /**
-     * Return the current character in the normalized text->
+     * Return the current character in the normalized text.
      * @return The codepoint as an int
      * @stable ICU 2.8
      */
@@ -872,10 +872,10 @@
      * while {@link #next} and {@link #previous} iterate through characters
      * in the normalized <em>output</em>.  This means that there is not
      * necessarily a one-to-one correspondence between characters returned
-     * by <tt>next</tt> and <tt>previous</tt> and the indices passed to and
-     * returned from <tt>setIndex</tt> and {@link #getIndex}.
-     * <p>
-     * @param index the desired index in the input text->
+     * by {@code next} and {@code previous} and the indices passed to and
+     * returned from {@code setIndex} and {@link #getIndex}.
+     *
+     * @param index the desired index in the input text.
      *
      * @return   the first normalized character that is the result of iterating
      *            forward starting at the given index.
@@ -894,8 +894,8 @@
 
     /**
      * Retrieve the index of the start of the input text. This is the begin
-     * index of the <tt>CharacterIterator</tt> or the start (i.e. 0) of the
-     * <tt>String</tt> over which this <tt>Normalizer</tt> is iterating
+     * index of the {@code CharacterIterator} or the start (i.e. 0) of the
+     * {@code String} over which this {@code Normalizer} is iterating
      * @deprecated ICU 2.2. Use startIndex() instead.
      * @return The codepoint as an int
      * @see #startIndex
@@ -907,8 +907,8 @@
 
     /**
      * Retrieve the index of the end of the input text.  This is the end index
-     * of the <tt>CharacterIterator</tt> or the length of the <tt>String</tt>
-     * over which this <tt>Normalizer</tt> is iterating
+     * of the {@code CharacterIterator} or the length of the {@code String}
+     * over which this {@code Normalizer} is iterating
      * @deprecated ICU 2.2. Use endIndex() instead.
      * @return The codepoint as an int
      * @see #endIndex
@@ -927,9 +927,9 @@
      * <b>Note:</b> This method sets the position in the <em>input</em>, while
      * {@link #next} and {@link #previous} iterate through characters in the
      * <em>output</em>.  This means that there is not necessarily a one-to-one
-     * correspondence between characters returned by <tt>next</tt> and
-     * <tt>previous</tt> and the indices passed to and returned from
-     * <tt>setIndex</tt> and {@link #getIndex}.
+     * correspondence between characters returned by {@code next} and
+     * {@code previous} and the indices passed to and returned from
+     * {@code setIndex} and {@link #getIndex}.
      * @return The current iteration position
      * @stable ICU 2.8
      */
@@ -942,9 +942,9 @@
     }
 
     /**
-     * Retrieve the index of the end of the input text->  This is the end index
-     * of the <tt>CharacterIterator</tt> or the length of the <tt>String</tt>
-     * over which this <tt>Normalizer</tt> is iterating
+     * 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
      * @return The current iteration position
      * @stable ICU 2.8
      */
@@ -963,9 +963,9 @@
      * return previously buffers characters in the old normalization mode
      * 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 <tt>setMode</tt>.
-     * <p>
-     * @param newMode the new mode for this <tt>Normalizer</tt>.
+     * {@link #last}, etc. after calling {@code setMode}.
+     *
+     * @param newMode the new mode for this {@code Normalizer}.
      * The supported modes are:
      * <ul>
      *  <li>{@link #COMPOSE}        - Unicode canonical decompositiion
@@ -985,7 +985,7 @@
         mode = newMode;
     }
     /**
-     * Return the basic operation performed by this <tt>Normalizer</tt>
+     * Return the basic operation performed by this {@code Normalizer}
      *
      * @see #setMode
      * @stable ICU 2.8
@@ -995,8 +995,8 @@
     }
 
     /**
-     * Set the input text over which this <tt>Normalizer</tt> will iterate.
-     * The iteration position is set to the beginning of the input text->
+     * Set the input text over which this {@code Normalizer} 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
      */
@@ -1011,8 +1011,8 @@
     }
 
     /**
-     * Set the input text over which this <tt>Normalizer</tt> will iterate.
-     * The iteration position is set to the beginning of the input text->
+     * Set the input text over which this {@code Normalizer} 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
      */
@@ -1571,7 +1571,7 @@
     //
 
     /**
-     * Creates a new <tt>Normalizer</tt> object for iterating over the
+     * 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
@@ -1646,7 +1646,6 @@
      * 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) {
         return isNormalized(str, form, UNICODE_LATEST);
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/RangeValueIterator.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/RangeValueIterator.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,12 +38,13 @@
 package sun.text.normalizer;
 
 /**
- * <p>Interface for enabling iteration over sets of <int index, int value>,
+ * <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>
+ * associated integer value.
  * <p>The result for each iteration is the consecutive range of
- * <int index, int value> with the same value. Result is represented by
- * <start, limit, value> where</p>
+ * {@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
@@ -56,10 +57,10 @@
  * Hence value(start) = value(start + 1) = .... = value(start + n) = .... =
  * value(limit - 1). However value(start -1) != value(start) and
  * value(limit) != value(start).
- * </p>
+ *
  * <p>Most implementations will be created by factory methods, such as the
  * character type iterator in UCharacter.getTypeIterator. See example below.
- * </p>
+ *
  * Example of use:<br>
  * <pre>
  * RangeValueIterator iterator = UCharacter.getTypeIterator();
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/Replaceable.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/Replaceable.java	Wed Jul 05 20:35:10 2017 +0200
@@ -71,10 +71,9 @@
  *   <li>If there is no previous character (i.e. start == 0), use the
  *   following character</li>
  *   <li>If there is no following character (i.e. the replaceable was
- *   empty), use default metadata<br>
+ *   empty), use default metadata</li>
  *   <li>If the code point U+FFFF is seen, it should be interpreted as
- *   a special marker having no metadata<li>
- *   </li>
+ *   a special marker having no metadata</li>
  * </ul>
  * If this is not the behavior, the subclass should document any differences.
  *
@@ -111,10 +110,10 @@
      * starting at index <code>dstStart</code> and ending at index
      * <code>dstStart + (srcLimit-srcStart) - 1</code>.
      *
-     * @param srcStart the beginning index to copy, inclusive; <code>0
-     * <= start <= limit</code>.
+     * @param srcStart the beginning index to copy, inclusive;
+     *        {@code 0 <= start <= limit}.
      * @param srcLimit the ending index to copy, exclusive;
-     * <code>start <= limit <= length()</code>.
+     *        {@code start <= limit <= length()}.
      * @param dst the destination array.
      * @param dstStart the start offset in the destination array.
      * @stable ICU 2.0
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/ReplaceableString.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/ReplaceableString.java	Wed Jul 05 20:35:10 2017 +0200
@@ -109,10 +109,10 @@
      * starting at index <code>dstStart</code> and ending at index
      * <code>dstStart + (srcLimit-srcStart) - 1</code>.
      *
-     * @param srcStart the beginning index to copy, inclusive; <code>0
-     * <= start <= limit</code>.
+     * @param srcStart the beginning index to copy, inclusive;
+     *        {@code 0 <= start <= limit}.
      * @param srcLimit the ending index to copy, exclusive;
-     * <code>start <= limit <= length()</code>.
+     *        {@code start <= limit <= length()}.
      * @param dst the destination array.
      * @param dstStart the start offset in the destination array.
      * @stable ICU 2.0
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/ReplaceableUCharacterIterator.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/ReplaceableUCharacterIterator.java	Wed Jul 05 20:35:10 2017 +0200
@@ -150,14 +150,12 @@
     }
 
     /**
-     * <p>Sets the currentIndex to the specified currentIndex in the text and returns that
+     * Sets the currentIndex to the specified currentIndex in the text and returns that
      * single UTF16 character at currentIndex.
-     * This assumes the text is stored as 16-bit code units.</p>
+     * This assumes the text is stored as 16-bit code units.
      * @param currentIndex the currentIndex within the text.
      * @exception IllegalArgumentException is thrown if an invalid currentIndex is
      *            supplied. i.e. currentIndex is out of bounds.
-     * @return the character at the specified currentIndex or DONE if the specified
-     *         currentIndex is equal to the end of the text.
      */
     public void setIndex(int currentIndex) {
         if (currentIndex < 0 || currentIndex > replaceable.length()) {
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/RuleCharacterIterator.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/RuleCharacterIterator.java	Wed Jul 05 20:35:10 2017 +0200
@@ -101,22 +101,25 @@
     public static final int DONE = -1;
 
     /**
-     * Bitmask option to enable parsing of variable names.  If (options &
-     * PARSE_VARIABLES) != 0, then an embedded variable will be expanded to
+     * 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 (options &
-     * PARSE_ESCAPES) != 0, then an embedded escape sequence will be expanded
+     * 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 (options &
-     * SKIP_WHITESPACE) != 0, then whitespace characters will be silently
+     * 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().
      */
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/SymbolTable.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/SymbolTable.java	Wed Jul 05 20:35:10 2017 +0200
@@ -78,7 +78,7 @@
 
     /**
      * Lookup the characters associated with this string and return it.
-     * Return <tt>null</tt> if no such name exists.  The resultant
+     * 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
@@ -91,7 +91,7 @@
 
     /**
      * Lookup the UnicodeMatcher associated with the given character, and
-     * return it.  Return <tt>null</tt> if not found.
+     * 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.
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/Trie.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/Trie.java	Wed Jul 05 20:35:10 2017 +0200
@@ -160,8 +160,10 @@
 
     /**
     * 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;
     /**
@@ -191,7 +193,7 @@
     /**
      * Number of index (stage 1) entries per lead surrogate.
      * Same as number of index entries for 1024 trail surrogates,
-     * ==0x400>>INDEX_STAGE_1_SHIFT_
+     * {@code ==0x400>>INDEX_STAGE_1_SHIFT_}
      */
     protected static final int SURROGATE_BLOCK_COUNT=(1<<SURROGATE_BLOCK_BITS);
     /** Length of the BMP portion of the index (stage 1) array. */
@@ -297,7 +299,7 @@
     /**
     * Internal trie getter from a code point.
     * Could be faster(?) but longer with
-    *   if((c32)<=0xd7ff) { (result)=_TRIE_GET_RAW(trie, data, 0, c32); }
+    * {@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
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/TrieIterator.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/TrieIterator.java	Wed Jul 05 20:35:10 2017 +0200
@@ -37,17 +37,17 @@
 package sun.text.normalizer;
 
 /**
- * <p>Class enabling iteration of the values in a Trie.</p>
+ * 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 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>
+ * 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>
+ * 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>
- * <p>See com.ibm.icu.text.UCharacterTypeIterator for examples of use.</p>
+ * 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
@@ -63,18 +63,17 @@
  * 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>
- * <p>There are basically 3 usage scenarios for porting:</p>
+ *
+ * <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>
+ *
  * <p>2) UTrieEnumValue and UTrieEnumRange both are implemented then implement
- * a subclass of TrieIterator, override the extract method and iterate, e.g
- * </p>
- * <p>utrie_enum(&normTrie, _enumPropertyStartsValue, _enumPropertyStartsRange,
- *               set);<br>
- * In Java :<br>
+ * 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){
@@ -90,17 +89,17 @@
  *     // port the implementation of _enumPropertyStartsRange
  * }
  * </pre>
- * </p>
+ *
  * <p>3) UTrieEnumRange is the only implemented callback then just implement
  * the while loop, when utrie_enum is called
- * <pre>
+ * <pre>{@code
  * // utrie_enum(&fcdTrie, NULL, _enumPropertyStartsRange, set);
  * TrieIterator fcdIter  = new TrieIterator(fcdTrieImpl.fcdTrie);
  * while(fcdIter.next(result)){
  *     set.add(result.start);
  * }
- * </pre>
- * </p>
+ * }</pre>
+ *
  * @author synwee
  * @see com.ibm.icu.impl.Trie
  * @see com.ibm.icu.lang.UCharacterTypeIterator
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/UCharacter.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/UCharacter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -128,7 +128,7 @@
  * Annex C: Compatibility Properties of UTS #18 Unicode Regular Expressions
  * (http://www.unicode.org/reports/tr18/#Compatibility_Properties).
  * </p>
- * <p>
+ * <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)
@@ -142,7 +142,7 @@
  * - cntrl:     getType(c)==CONTROL
  * - graph:     hasBinaryProperty(c, UProperty.POSIX_GRAPH)
  * - print:     hasBinaryProperty(c, UProperty.POSIX_PRINT)
- * </p>
+ * }</pre>
  * <p>
  * The C/POSIX character classes are also available in UnicodeSet patterns,
  * using patterns like [:graph:] or \p{graph}.
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/UCharacterIterator.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/UCharacterIterator.java	Wed Jul 05 20:35:10 2017 +0200
@@ -200,8 +200,7 @@
      * iterator obtained by calling <code>getLength()</code>.
      * <b>Usage:</b>
      *
-     * <code>
-     * <pre>
+     * <pre>{@code
      *         UChacterIterator iter = new UCharacterIterator.getInstance(text);
      *         char[] buf = new char[iter.getLength()];
      *         iter.getText(buf);
@@ -217,15 +216,14 @@
      *                 buf = new char[iter.getLength()];
      *             }
      *         }
-     * </pre>
-     * </code>
+     * }</pre>
      *
      * @param fillIn an array of chars to fill with the underlying UTF-16 code
      *         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 < 0.
+     *            room after offset in the array, or if offset {@literal <} 0.
      * @stable ICU 2.4
      */
     public abstract int getText(char[] fillIn, int offset);
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/UTF16.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/UTF16.java	Wed Jul 05 20:35:10 2017 +0200
@@ -38,26 +38,26 @@
 
 /**
  * <p>Standalone utility class providing UTF16 character conversions and
- * indexing conversions.</p>
+ * indexing conversions.
  * <p>Code that uses strings alone rarely need modification.
  * By design, UTF-16 does not allow overlap, so searching for strings is a safe
  * operation. Similarly, concatenation is always safe. Substringing is safe if
  * the start and end are both on UTF-32 boundaries. In normal code, the values
  * for start and end are on those boundaries, since they arose from operations
  * like searching. If not, the nearest UTF-32 boundaries can be determined
- * using <code>bounds()</code>.</p>
+ * using <code>bounds()</code>.
  * <strong>Examples:</strong>
  * <p>The following examples illustrate use of some of these methods.
- * <pre>
+ * <pre>{@code
  * // iteration forwards: Original
- * for (int i = 0; i &lt; s.length(); ++i) {
+ * for (int i = 0; i < s.length(); ++i) {
  *     char ch = s.charAt(i);
  *     doSomethingWith(ch);
  * }
  *
  * // iteration forwards: Changes for UTF-32
  * int ch;
- * for (int i = 0; i &lt; s.length(); i+=UTF16.getCharCount(ch)) {
+ * for (int i = 0; i < s.length(); i+=UTF16.getCharCount(ch)) {
  *     ch = UTF16.charAt(s,i);
  *     doSomethingWith(ch);
  * }
@@ -74,7 +74,7 @@
  *     ch = UTF16.charAt(s,i);
  *     doSomethingWith(ch);
  * }
- * </pre>
+ * }</pre>
  * <strong>Notes:</strong>
  * <ul>
  *   <li>
@@ -515,12 +515,12 @@
 
     /**
      * <p>Converts argument code point and returns a String object representing
-     * the code point's value in UTF16 format.</p>
+     * the code point's value in UTF16 format.
      * <p>This method does not check for the validity of the codepoint, the
      * results are not guaranteed if a invalid codepoint is passed as
-     * argument.</p>
+     * argument.
      * <p>The result is a string whose length is 1 for non-supplementary code
-     * points, 2 otherwise.</p>
+     * points, 2 otherwise.
      * @param ch code point
      * @return string representation of the code point
      */
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/UnicodeMatcher.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/UnicodeMatcher.java	Wed Jul 05 20:35:10 2017 +0200
@@ -45,7 +45,8 @@
 public interface UnicodeMatcher {
 
     /**
-     * The character at index i, where i < contextStart || i >= contextLimit,
+     * 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.
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/UnicodeSet.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/UnicodeSet.java	Wed Jul 05 20:35:10 2017 +0200
@@ -107,8 +107,8 @@
  *     </tr>
  *     <tr>
  *       <td nowrap valign="top" align="left"><code>[a{ab}{ac}]</code></td>
- *       <td valign="top">The character 'a' and the multicharacter strings &quot;ab&quot; and
- *       &quot;ac&quot;</td>
+ *       <td valign="top">The character 'a' and the multicharacter strings "ab" and
+ *       "ac"</td>
  *     </tr>
  *     <tr>
  *       <td nowrap valign="top" align="left"><code>[\p{Lu}]</code></td>
@@ -148,10 +148,10 @@
  * literal.  Thus "[a\\-b]", "[-ab]", and "[ab-]" all indicate the same
  * set of three characters, 'a', 'b', and '-'.
  *
- * <p>Sets may be intersected using the '&' operator or the asymmetric
+ * <p>Sets may be intersected using the {@literal '&'} operator or the asymmetric
  * set difference may be taken using the '-' operator, for example,
- * "[[:L:]&[\\u0000-\\u0FFF]]" indicates the set of all Unicode letters
- * with values less than 4096.  Operators ('&' and '|') have equal
+ * "{@code [[:L:]&[\\u0000-\\u0FFF]]}" indicates the set of all Unicode letters
+ * with values less than 4096.  Operators ({@literal '&'} and '|') have equal
  * precedence and bind left-to-right.  Thus
  * "[[:L:]-[a-z]-[\\u0100-\\u01FF]]" is equivalent to
  * "[[[:L:]-[a-z]]-[\\u0100-\\u01FF]]".  This only really matters for
@@ -166,7 +166,7 @@
  * that is, U+0000 through 'a'-1 and 'z'+1 through U+10FFFF
  * <tr valign=top><td nowrap><code>[[<em>pat1</em>][<em>pat2</em>]]</code>
  * <td>The union of sets specified by <em>pat1</em> and <em>pat2</em>
- * <tr valign=top><td nowrap><code>[[<em>pat1</em>]&[<em>pat2</em>]]</code>
+ * <tr valign=top><td nowrap><code>[[<em>pat1</em>]&amp;[<em>pat2</em>]]</code>
  * <td>The intersection of sets specified by <em>pat1</em> and <em>pat2</em>
  * <tr valign=top><td nowrap><code>[[<em>pat1</em>]-[<em>pat2</em>]]</code>
  * <td>The asymmetric difference of sets specified by <em>pat1</em> and
@@ -227,7 +227,7 @@
  *     </tr>
  *     <tr>
  *       <td nowrap valign="top" align="right"><code>property :=&nbsp; </code></td>
- *       <td valign="top"><em>a Unicode property set pattern</td>
+ *       <td valign="top"><em>a Unicode property set pattern</em></td>
  *     </tr>
  *   </table>
  *   <br>
@@ -337,8 +337,8 @@
     }
 
     /**
-     * Constructs a set containing the given range. If <code>end >
-     * start</code> then an empty set is created.
+     * Constructs a set containing the given range.
+     * If {@code end > start} then an empty set is created.
      *
      * @param start first character, inclusive, of range
      * @param end last character, inclusive, of range
@@ -651,7 +651,7 @@
      * Adds the specified multicharacter to this set if it is not already
      * present.  If this set already contains the multicharacter,
      * the call leaves this set unchanged.
-     * Thus "ch" => {"ch"}
+     * Thus {@code "ch" => {"ch"}}
      * <br><b>Warning: you cannot add an empty string ("") to a UnicodeSet.</b>
      * @param s the source string
      * @return this object, for chaining
@@ -691,7 +691,7 @@
     /**
      * Complements the specified range in this set.  Any character in
      * the range will be removed if it is in this set, or will be
-     * added if it is not in this set.  If <code>end > start</code>
+     * added if it is not in this set.  If {@code end > start}
      * then an empty range is complemented, leaving the set unchanged.
      *
      * @param start first character, inclusive, of range to be removed
@@ -1698,8 +1698,8 @@
      * 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
-     * @param valueAlias
+     * @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
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/UnicodeSetIterator.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/UnicodeSetIterator.java	Wed Jul 05 20:35:10 2017 +0200
@@ -73,35 +73,35 @@
 public class UnicodeSetIterator {
 
     /**
-     * Value of <tt>codepoint</tt> if the iterator points to a string.
-     * If <tt>codepoint == IS_STRING</tt>, then examine
-     * <tt>string</tt> for the current iteration result.
+     * 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 <tt>IS_STRING</tt>, if
+     * 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 <tt>nextRange()</tt>,
-     * <tt>codepointEnd</tt> contains the inclusive end of the
-     * iteration range, if <tt>codepoint != IS_STRING</tt>.  If
-     * iterating over code points using <tt>next()</tt>, or if
-     * <tt>codepoint == IS_STRING</tt>, then the value of
-     * <tt>codepointEnd</tt> is undefined.
+     * 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 <tt>codepoint == IS_STRING</tt>, then <tt>string</tt> points
-     * to the current string.  If <tt>codepoint != IS_STRING</tt>, the
-     * value of <tt>string</tt> is undefined.
+     * 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;
@@ -118,17 +118,17 @@
     /**
      * 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 <tt>codepoint == IS_STRING</tt>, the value is a
-     * string in the <tt>string</tt> field.  Otherwise the value is a
-     * range of one or more code points from <tt>codepoint</tt> to
-     * <tt>codepointeEnd</tt> inclusive.
+     * 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.  <tt>string</tt> is undefined
-     * unless <tt>codepoint == IS_STRING</tt>.  Do not mix calls to
-     * <tt>next()</tt> and <tt>nextRange()</tt> without calling
-     * <tt>reset()</tt> between them.  The results of doing so 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
@@ -162,8 +162,8 @@
     /**
      * 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 <tt>set</tt> is valid.
-     * @param set the set to iterate over.
+     * so long as {@code set} is valid.
+     * @param uset the set to iterate over.
      * @stable ICU 2.0
      */
     public void reset(UnicodeSet uset) {
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/Utility.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/Utility.java	Wed Jul 05 20:35:10 2017 +0200
@@ -227,7 +227,7 @@
 
     /**
      * Convert a integer to size width hex uppercase digits.
-     * E.g., hex('a', 4, str) => "0041".
+     * 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.
      */
@@ -237,7 +237,7 @@
 
     /**
      * Convert a integer to size width (minimum) hex uppercase digits.
-     * E.g., hex('a', 4, str) => "0041".  If the integer requires more
+     * E.g., {@code hex('a', 4, str) => "0041"}.  If the integer requires more
      * than width digits, more will be used.
      */
     public static String hex(int ch, int width) {
@@ -334,8 +334,8 @@
     }
 
     /**
-     * Escape unprintable characters using <backslash>uxxxx notation
-     * for U+0000 to U+FFFF and <backslash>Uxxxxxxxx for U+10000 and
+     * Escape unprintable characters using {@code <backslash>uxxxx} notation
+     * for U+0000 to U+FFFF and {@code <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.
--- a/jdk/src/java.base/share/classes/sun/text/normalizer/VersionInfo.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/share/classes/sun/text/normalizer/VersionInfo.java	Wed Jul 05 20:35:10 2017 +0200
@@ -53,7 +53,7 @@
      * @param version version String in the format of "major.minor.milli.micro"
      *                or "major.minor.milli" or "major.minor" or "major",
      *                where major, minor, milli, micro are non-negative numbers
-     *                <= 255. If the trailing version numbers are
+     *                {@literal <=} 255. If the trailing version numbers are
      *                not specified they are taken as 0s. E.g. Version "3.1" is
      *                equivalent to "3.1.0.0".
      * @return an instance of VersionInfo with the argument version.
@@ -98,12 +98,12 @@
 
     /**
      * Returns an instance of VersionInfo with the argument version.
-     * @param major major version, non-negative number <= 255.
-     * @param minor minor version, non-negative number <= 255.
-     * @param milli milli version, non-negative number <= 255.
-     * @param micro micro version, non-negative number <= 255.
+     * @param major major version, non-negative number {@literal <=} 255.
+     * @param minor minor version, non-negative number {@literal <=} 255.
+     * @param milli milli version, non-negative number {@literal <=} 255.
+     * @param micro micro version, non-negative number {@literal <=} 255.
      * @exception throws an IllegalArgumentException when either arguments are
-     *                                     negative or > 255
+     *                                     negative or {@literal >} 255
      * @stable ICU 2.6
      */
     public static VersionInfo getInstance(int major, int minor, int milli,
--- a/jdk/src/java.base/unix/classes/sun/nio/fs/UnixChannelFactory.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/unix/classes/sun/nio/fs/UnixChannelFactory.java	Wed Jul 05 20:35:10 2017 +0200
@@ -270,22 +270,6 @@
             throw x;
         }
 
-        // fail if the file is a directory
-        if (flags.read) {
-            UnixException exc = null;
-            try {
-                if (UnixFileAttributes.get(fd).isDirectory()) {
-                    exc = new UnixException(EISDIR);
-                }
-            } catch (UnixException x) {
-                exc = x;
-            }
-            if (exc != null) {
-                close(fd);
-                throw exc;
-            }
-        }
-
         // unlink file immediately if delete on close. The spec is clear that
         // an implementation cannot guarantee to unlink the correct file when
         // replaced by an attacker after it is opened.
--- a/jdk/src/java.base/unix/native/libnio/ch/FileDispatcherImpl.c	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/unix/native/libnio/ch/FileDispatcherImpl.c	Wed Jul 05 20:35:10 2017 +0200
@@ -148,6 +148,13 @@
     jint fd = fdval(env, fdo);
     int result = 0;
 
+#ifdef MACOSX
+    result = fcntl(fd, F_FULLFSYNC);
+    if (result == -1 && errno == ENOTSUP) {
+        /* Try fsync() in case F_FULLSYUNC is not implemented on the file system. */
+        result = fsync(fd);
+    }
+#else /* end MACOSX, begin not-MACOSX */
     if (md == JNI_FALSE) {
         result = fdatasync(fd);
     } else {
@@ -163,9 +170,10 @@
         if (getfl >= 0 && (getfl & O_ACCMODE) == O_RDONLY) {
             return 0;
         }
-#endif
+#endif /* _AIX */
         result = fsync(fd);
     }
+#endif /* not-MACOSX */
     return handle(env, result, "Force failed");
 }
 
--- a/jdk/src/java.base/windows/native/libjli/java_md.c	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.base/windows/native/libjli/java_md.c	Wed Jul 05 20:35:10 2017 +0200
@@ -990,6 +990,26 @@
     return JNI_FALSE;
 }
 
+int
+filterArgs(StdArg *stdargs, const int nargc, StdArg **pargv) {
+    StdArg* argv = NULL;
+    int nargs = 0;
+    int i;
+
+    /* Copy the non-vm args */
+    for (i = 0; i < nargc ; i++) {
+        const char *arg = stdargs[i].arg;
+        if (arg[0] == '-' && arg[1] == 'J')
+            continue;
+        argv = (StdArg*) JLI_MemRealloc(argv, (nargs+1) * sizeof(StdArg));
+        argv[nargs].arg = JLI_StringDup(arg);
+        argv[nargs].has_wildcard = stdargs[i].has_wildcard;
+        nargs++;
+    }
+    *pargv = argv;
+    return nargs;
+}
+
 /*
  * At this point we have the arguments to the application, and we need to
  * check with original stdargs in order to compare which of these truly
@@ -1005,8 +1025,9 @@
     char *ostart, *astart, **nargv;
     jboolean needs_expansion = JNI_FALSE;
     jmethodID mid;
-    int stdargc;
+    int filteredargc, stdargc;
     StdArg *stdargs;
+    StdArg *filteredargs;
     jclass cls = GetLauncherHelperClass(env);
     NULL_CHECK0(cls);
 
@@ -1017,6 +1038,8 @@
     stdargs = JLI_GetStdArgs();
     stdargc = JLI_GetStdArgc();
 
+    filteredargc = filterArgs(stdargs, stdargc, &filteredargs);
+
     // sanity check, this should never happen
     if (argc > stdargc) {
         JLI_TraceLauncher("Warning: app args is larger than the original, %d %d\n", argc, stdargc);
@@ -1025,8 +1048,8 @@
     }
 
     // sanity check, match the args we have, to the holy grail
-    idx = stdargc - argc;
-    ostart = stdargs[idx].arg;
+    idx = filteredargc - argc;
+    ostart = filteredargs[idx].arg;
     astart = strv[0];
     // sanity check, ensure that the first argument of the arrays are the same
     if (JLI_StrCmp(ostart, astart) != 0) {
@@ -1039,8 +1062,8 @@
     // make a copy of the args which will be expanded in java if required.
     nargv = (char **)JLI_MemAlloc(argc * sizeof(char*));
     for (i = 0, j = idx; i < argc; i++, j++) {
-        jboolean arg_expand = (JLI_StrCmp(stdargs[j].arg, strv[i]) == 0)
-                                ? stdargs[j].has_wildcard
+        jboolean arg_expand = (JLI_StrCmp(filteredargs[j].arg, strv[i]) == 0)
+                                ? filteredargs[j].has_wildcard
                                 : JNI_FALSE;
         if (needs_expansion == JNI_FALSE)
             needs_expansion = arg_expand;
@@ -1077,5 +1100,6 @@
         JLI_MemFree(nargv[i]);
     }
     JLI_MemFree(nargv);
+    JLI_MemFree(filteredargs);
     return outArray;
 }
--- a/jdk/src/java.logging/share/classes/java/util/logging/LogManager.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.logging/share/classes/java/util/logging/LogManager.java	Wed Jul 05 20:35:10 2017 +0200
@@ -33,6 +33,7 @@
 import java.lang.ref.WeakReference;
 import java.util.concurrent.ConcurrentHashMap;
 import java.util.concurrent.CopyOnWriteArrayList;
+import java.util.concurrent.locks.ReentrantLock;
 import sun.misc.JavaAWTAccess;
 import sun.misc.ManagedLocalsThread;
 import sun.misc.SharedSecrets;
@@ -180,10 +181,16 @@
     // initialization has been done)
     private volatile boolean readPrimordialConfiguration;
     // Have we initialized global (root) handlers yet?
-    // This gets set to false in readConfiguration
-    private boolean initializedGlobalHandlers = true;
-    // True if JVM death is imminent and the exit hook has been called.
-    private boolean deathImminent;
+    // This gets set to STATE_UNINITIALIZED in readConfiguration
+    private static final int
+            STATE_INITIALIZED = 0, // initial state
+            STATE_INITIALIZING = 1,
+            STATE_READING_CONFIG = 2,
+            STATE_UNINITIALIZED = 3,
+            STATE_SHUTDOWN = 4;    // terminal state
+    private volatile int globalHandlersState; // = STATE_INITIALIZED;
+    // A concurrency lock for reset(), readConfiguration() and Cleaner.
+    private final ReentrantLock configurationLock = new ReentrantLock();
 
     // This list contains the loggers for which some handlers have been
     // explicitly configured in the configuration file.
@@ -264,13 +271,12 @@
             // before synchronized block. Otherwise deadlocks are possible.
             LogManager mgr = manager;
 
-            // If the global handlers haven't been initialized yet, we
-            // don't want to initialize them just so we can close them!
-            synchronized (LogManager.this) {
-                // Note that death is imminent.
-                deathImminent = true;
-                initializedGlobalHandlers = true;
-            }
+            // set globalHandlersState to STATE_SHUTDOWN atomically so that
+            // no attempts are made to (re)initialize the handlers or (re)read
+            // the configuration again. This is terminal state.
+            configurationLock.lock();
+            globalHandlersState = STATE_SHUTDOWN;
+            configurationLock.unlock();
 
             // Do a reset to close all active handlers.
             reset();
@@ -1314,8 +1320,14 @@
 
     public void reset() throws SecurityException {
         checkPermission();
+
         List<CloseOnReset> persistent;
-        synchronized (this) {
+
+        // We don't want reset() and readConfiguration()
+        // to run in parallel
+        configurationLock.lock();
+        try {
+            // install new empty properties
             props = new Properties();
             // make sure we keep the loggers persistent until reset is done.
             // Those are the loggers for which we previously created a
@@ -1323,26 +1335,41 @@
             // from being gc'ed until those handlers are closed.
             persistent = new ArrayList<>(closeOnResetLoggers);
             closeOnResetLoggers.clear();
-            // Since we are doing a reset we no longer want to initialize
-            // the global handlers, if they haven't been initialized yet.
-            initializedGlobalHandlers = true;
+
+            // if reset has been called from shutdown-hook (Cleaner),
+            // or if reset has been called from readConfiguration() which
+            // already holds the lock and will change the state itself,
+            // then do not change state here...
+            if (globalHandlersState != STATE_SHUTDOWN &&
+                globalHandlersState != STATE_READING_CONFIG) {
+                // ...else user called reset()...
+                // Since we are doing a reset we no longer want to initialize
+                // the global handlers, if they haven't been initialized yet.
+                globalHandlersState = STATE_INITIALIZED;
+            }
+
+            for (LoggerContext cx : contexts()) {
+                resetLoggerContext(cx);
+            }
+
+            persistent.clear();
+        } finally {
+            configurationLock.unlock();
         }
-        for (LoggerContext cx : contexts()) {
-            Enumeration<String> enum_ = cx.getLoggerNames();
-            while (enum_.hasMoreElements()) {
-                String name = enum_.nextElement();
-                Logger logger = cx.findLogger(name);
-                if (logger != null) {
-                    resetLogger(logger);
-                }
+    }
+
+    private void resetLoggerContext(LoggerContext cx) {
+        Enumeration<String> enum_ = cx.getLoggerNames();
+        while (enum_.hasMoreElements()) {
+            String name = enum_.nextElement();
+            Logger logger = cx.findLogger(name);
+            if (logger != null) {
+                resetLogger(logger);
             }
         }
-        persistent.clear();
     }
 
-    // Private method to reset an individual target logger.
-    private void resetLogger(Logger logger) {
-        // Close all the Logger's handlers.
+    private void closeHandlers(Logger logger) {
         Handler[] targets = logger.getHandlers();
         for (Handler h : targets) {
             logger.removeHandler(h);
@@ -1352,6 +1379,14 @@
                 // Problems closing a handler?  Keep going...
             }
         }
+    }
+
+    // Private method to reset an individual target logger.
+    private void resetLogger(Logger logger) {
+        // Close all the Logger handlers.
+        closeHandlers(logger);
+
+        // Reset Logger level
         String name = logger.getName();
         if (name != null && name.equals("")) {
             // This is the root logger.
@@ -1408,48 +1443,74 @@
      */
     public void readConfiguration(InputStream ins) throws IOException, SecurityException {
         checkPermission();
-        reset();
 
-        // Load the properties
+        // We don't want reset() and readConfiguration() to run
+        // in parallel.
+        configurationLock.lock();
         try {
-            props.load(ins);
-        } catch (IllegalArgumentException x) {
-            // props.load may throw an IllegalArgumentException if the stream
-            // contains malformed Unicode escape sequences.
-            // We wrap that in an IOException as readConfiguration is
-            // specified to throw IOException if there are problems reading
-            // from the stream.
-            // Note: new IOException(x.getMessage(), x) allow us to get a more
-            // concise error message than new IOException(x);
-            throw new IOException(x.getMessage(), x);
+            if (globalHandlersState == STATE_SHUTDOWN) {
+                // already in terminal state: don't even bother
+                // to read the configuration
+                return;
+            }
+
+            // change state to STATE_READING_CONFIG to signal reset() to not change it
+            globalHandlersState = STATE_READING_CONFIG;
+            try {
+                // reset configuration which leaves globalHandlersState at STATE_READING_CONFIG
+                // so that while reading configuration, any ongoing logging requests block and
+                // wait for the outcome (see the end of this try statement)
+                reset();
+
+                try {
+                    // Load the properties
+                    props.load(ins);
+                } catch (IllegalArgumentException x) {
+                    // props.load may throw an IllegalArgumentException if the stream
+                    // contains malformed Unicode escape sequences.
+                    // We wrap that in an IOException as readConfiguration is
+                    // specified to throw IOException if there are problems reading
+                    // from the stream.
+                    // Note: new IOException(x.getMessage(), x) allow us to get a more
+                    // concise error message than new IOException(x);
+                    throw new IOException(x.getMessage(), x);
+                }
+
+                // Instantiate new configuration objects.
+                String names[] = parseClassNames("config");
+
+                for (String word : names) {
+                    try {
+                        Class<?> clz = ClassLoader.getSystemClassLoader().loadClass(word);
+                        clz.newInstance();
+                    } catch (Exception ex) {
+                        System.err.println("Can't load config class \"" + word + "\"");
+                        System.err.println("" + ex);
+                        // ex.printStackTrace();
+                    }
+                }
+
+                // Set levels on any pre-existing loggers, based on the new properties.
+                setLevelsOnExistingLoggers();
+
+                // Note that we need to reinitialize global handles when
+                // they are first referenced.
+                globalHandlersState = STATE_UNINITIALIZED;
+            } catch (Throwable t) {
+                // If there were any trouble, then set state to STATE_INITIALIZED
+                // so that no global handlers reinitialization is performed on not fully
+                // initialized configuration.
+                globalHandlersState = STATE_INITIALIZED;
+                // re-throw
+                throw t;
+            }
+        } finally {
+            configurationLock.unlock();
         }
 
-        // Instantiate new configuration objects.
-        String names[] = parseClassNames("config");
-
-        for (String word : names) {
-            try {
-                Class<?> clz = ClassLoader.getSystemClassLoader().loadClass(word);
-                clz.newInstance();
-            } catch (Exception ex) {
-                System.err.println("Can't load config class \"" + word + "\"");
-                System.err.println("" + ex);
-                // ex.printStackTrace();
-            }
-        }
-
-        // Set levels on any pre-existing loggers, based on the new properties.
-        setLevelsOnExistingLoggers();
-
-        try {
-            invokeConfigurationListeners();
-        } finally {
-            // Note that we need to reinitialize global handles when
-            // they are first referenced.
-            synchronized (this) {
-                initializedGlobalHandlers = false;
-            }
-        }
+        // should be called out of lock to avoid dead-lock situations
+        // when user code is involved
+        invokeConfigurationListeners();
     }
 
     /**
@@ -1576,20 +1637,41 @@
     // Private method to load the global handlers.
     // We do the real work lazily, when the global handlers
     // are first used.
-    private synchronized void initializeGlobalHandlers() {
-        if (initializedGlobalHandlers) {
+    private void initializeGlobalHandlers() {
+        int state = globalHandlersState;
+        if (state == STATE_INITIALIZED ||
+            state == STATE_SHUTDOWN) {
+            // Nothing to do: return.
             return;
         }
 
-        initializedGlobalHandlers = true;
-
-        if (deathImminent) {
-            // Aaargh...
-            // The VM is shutting down and our exit hook has been called.
-            // Avoid allocating global handlers.
-            return;
+        // If we have not initialized global handlers yet (or need to
+        // reinitialize them), lets do it now (this case is indicated by
+        // globalHandlersState == STATE_UNINITIALIZED).
+        // If we are in the process of initializing global handlers we
+        // also need to lock & wait (this case is indicated by
+        // globalHandlersState == STATE_INITIALIZING).
+        // If we are in the process of reading configuration we also need to
+        // wait to see what the outcome will be (this case
+        // is indicated by globalHandlersState == STATE_READING_CONFIG)
+        // So in either case we need to wait for the lock.
+        configurationLock.lock();
+        try {
+            if (globalHandlersState != STATE_UNINITIALIZED) {
+                return; // recursive call or nothing to do
+            }
+            // set globalHandlersState to STATE_INITIALIZING first to avoid
+            // getting an infinite recursion when loadLoggerHandlers(...)
+            // is going to call addHandler(...)
+            globalHandlersState = STATE_INITIALIZING;
+            try {
+                loadLoggerHandlers(rootLogger, null, "handlers");
+            } finally {
+                globalHandlersState = STATE_INITIALIZED;
+            }
+        } finally {
+            configurationLock.unlock();
         }
-        loadLoggerHandlers(rootLogger, null, "handlers");
     }
 
     static final Permission controlPermission = new LoggingPermission("control", null);
@@ -1684,7 +1766,7 @@
 
     // Private method to be called when the configuration has
     // changed to apply any level settings to any pre-existing loggers.
-    synchronized private void setLevelsOnExistingLoggers() {
+    private void setLevelsOnExistingLoggers() {
         Enumeration<?> enum_ = props.propertyNames();
         while (enum_.hasMoreElements()) {
             String key = (String)enum_.nextElement();
--- a/jdk/src/java.logging/share/classes/java/util/logging/package.html	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.logging/share/classes/java/util/logging/package.html	Wed Jul 05 20:35:10 2017 +0200
@@ -30,8 +30,7 @@
 <body bgcolor="white">
 <P>
 Provides the classes and interfaces of 
-the Java<SUP><FONT SIZE="-2">TM</FONT></SUP> 2
- platform's core logging facilities.
+the Java&trade; 2 platform's core logging facilities.
 The central goal of the logging APIs is to support maintaining and servicing
 software at customer sites. 
 
--- a/jdk/src/java.management/share/classes/com/sun/jmx/mbeanserver/DefaultMXBeanMappingFactory.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.management/share/classes/com/sun/jmx/mbeanserver/DefaultMXBeanMappingFactory.java	Wed Jul 05 20:35:10 2017 +0200
@@ -79,44 +79,46 @@
 
 /**
  *   <p>A converter between Java types and the limited set of classes
- *   defined by Open MBeans.</p>
+ *   defined by Open MBeans.
  *
- *   <p>A Java type is an instance of java.lang.reflect.Type.  For our
+ *   <p>A Java type is an instance of java.lang.reflect.Type. For our
  *   purposes, it is either a Class, such as String.class or int.class;
- *   or a ParameterizedType, such as List<String> or Map<Integer,
- *   String[]>.  On J2SE 1.4 and earlier, it can only be a Class.</p>
+ *   or a ParameterizedType, such as {@code List<String>} or
+ *   {@code Map<Integer, String[]>}.
+ *   On J2SE 1.4 and earlier, it can only be a Class.
  *
- *   <p>Each Type is associated with an DefaultMXBeanMappingFactory.  The
- *   DefaultMXBeanMappingFactory defines an OpenType corresponding to the Type, plus a
- *   Java class corresponding to the OpenType.  For example:</p>
+ *   <p>Each Type is associated with an DefaultMXBeanMappingFactory. The
+ *   DefaultMXBeanMappingFactory defines an
+ *   OpenType corresponding to the Type, plus a
+ *   Java class corresponding to the OpenType. For example:
  *
- *   <pre>
+ *   <pre>{@code
  *   Type                     Open class     OpenType
  *   ----                     ----------     --------
- *   Integer                Integer        SimpleType.INTEGER
- *   int                            int            SimpleType.INTEGER
- *   Integer[]              Integer[]      ArrayType(1, SimpleType.INTEGER)
- *   int[]                  Integer[]      ArrayType(SimpleType.INTEGER, true)
- *   String[][]             String[][]     ArrayType(2, SimpleType.STRING)
- *   List<String>                   String[]       ArrayType(1, SimpleType.STRING)
+ *   Integer                  Integer        SimpleType.INTEGER
+ *   int                      int            SimpleType.INTEGER
+ *   Integer[]                Integer[]      ArrayType(1, SimpleType.INTEGER)
+ *   int[]                    Integer[]      ArrayType(SimpleType.INTEGER, true)
+ *   String[][]               String[][]     ArrayType(2, SimpleType.STRING)
+ *   List<String>             String[]       ArrayType(1, SimpleType.STRING)
  *   ThreadState (an Enum)    String         SimpleType.STRING
- *   Map<Integer, String[]>   TabularData          TabularType(
+ *   Map<Integer, String[]>   TabularData    TabularType(
  *                                           CompositeType(
  *                                             {"key", SimpleType.INTEGER},
  *                                             {"value",
  *                                               ArrayType(1,
  *                                                SimpleType.STRING)}),
  *                                           indexNames={"key"})
- *   </pre>
+ *   }</pre>
  *
  *   <p>Apart from simple types, arrays, and collections, Java types are
  *   converted through introspection into CompositeType.  The Java type
  *   must have at least one getter (method such as "int getSize()" or
  *   "boolean isBig()"), and we must be able to deduce how to
  *   reconstruct an instance of the Java class from the values of the
- *   getters using one of various heuristics.</p>
+ *   getters using one of various heuristics.
  *
- * @since 1.6
+ *  @since 1.6
  */
 public class DefaultMXBeanMappingFactory extends MXBeanMappingFactory {
     static abstract class NonNullMXBeanMapping extends MXBeanMapping {
@@ -148,8 +150,8 @@
         throws OpenDataException;
 
         /**
-         * <p>True if and only if this MXBeanMapping's toOpenValue and
-         * fromOpenValue methods are the identity function.</p>
+         * True if and only if this MXBeanMapping's toOpenValue and
+         * fromOpenValue methods are the identity function.
          */
         boolean isIdentity() {
             return false;
--- a/jdk/src/java.management/share/classes/com/sun/jmx/remote/internal/ServerCommunicatorAdmin.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.management/share/classes/com/sun/jmx/remote/internal/ServerCommunicatorAdmin.java	Wed Jul 05 20:35:10 2017 +0200
@@ -57,8 +57,8 @@
      * <code>rspOutgoing</code> to inform that a response is sent out
      * for the received request.
      * @return the value of the termination flag:
-     * <ul><code>true</code> if the connection is already being terminated,
-     * <br><code>false</code> otherwise.</ul>
+     *         true if the connection is already being terminated,
+     *         false otherwise.
      */
     public boolean reqIncoming() {
         if (logger.traceOn()) {
@@ -80,8 +80,8 @@
     /**
      * Tells that a response is sent out for a received request.
      * @return the value of the termination flag:
-     * <ul><code>true</code> if the connection is already being terminated,
-     * <br><code>false</code> otherwise.</ul>
+     *         true if the connection is already being terminated,
+     *         false otherwise.
      */
     public boolean rspOutgoing() {
         if (logger.traceOn()) {
--- a/jdk/src/java.management/share/classes/com/sun/jmx/remote/util/EnvHelp.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.management/share/classes/com/sun/jmx/remote/util/EnvHelp.java	Wed Jul 05 20:35:10 2017 +0200
@@ -55,17 +55,17 @@
 public class EnvHelp {
 
     /**
-     * <p>Name of the attribute that specifies a default class loader
+     * Name of the attribute that specifies a default class loader
      * object.
-     * The value associated with this attribute is a ClassLoader object</p>
+     * The value associated with this attribute is a ClassLoader object.
      */
     private static final String DEFAULT_CLASS_LOADER =
         JMXConnectorFactory.DEFAULT_CLASS_LOADER;
 
     /**
-     * <p>Name of the attribute that specifies a default class loader
-     *    ObjectName.
-     * The value associated with this attribute is an ObjectName object</p>
+     * Name of the attribute that specifies a default class loader
+     * ObjectName.
+     * The value associated with this attribute is an ObjectName object.
      */
     private static final String DEFAULT_CLASS_LOADER_NAME =
         JMXConnectorServerFactory.DEFAULT_CLASS_LOADER_NAME;
@@ -74,7 +74,6 @@
      * Get the Connector Server default class loader.
      * <p>
      * Returns:
-     * <p>
      * <ul>
      * <li>
      *     The ClassLoader object found in <var>env</var> for
@@ -114,6 +113,7 @@
      *     <code>jmx.remote.default.class.loader.name</code> is specified
      *     but <var>mbs</var> is null.
      * </li>
+     * </ul>
      * @exception InstanceNotFoundException if
      * <code>jmx.remote.default.class.loader.name</code> is specified
      * and the ClassLoader MBean is not found in <var>mbs</var>.
@@ -172,7 +172,6 @@
      * Get the Connector Client default class loader.
      * <p>
      * Returns:
-     * <p>
      * <ul>
      * <li>
      *     The ClassLoader object found in <var>env</var> for
@@ -232,7 +231,7 @@
     /**
      * Returns the cause field of a {@code Throwable} object.
      * The cause field can be got only if <var>t</var> has an
-     * {@link Throwable#getCause()} method (JDK Version >= 1.4)
+     * {@link Throwable#getCause()} method (JDK Version {@literal >=} 1.4)
      * @param t {@code Throwable} on which the cause must be set.
      * @return the cause if getCause() succeeded and the got value is not
      * null, otherwise return the <var>t</var>.
@@ -254,7 +253,7 @@
 
 
     /**
-     * <p>Name of the attribute that specifies the size of a notification
+     * Name of the attribute that specifies the size of a notification
      * buffer for a connector server. The default value is 1000.
      */
     public static final String BUFFER_SIZE_PROPERTY =
@@ -316,10 +315,10 @@
     }
 
     /**
-     * <p>Name of the attribute that specifies the maximum number of
-     * notifications that a client will fetch from its server.. The
+     * Name of the attribute that specifies the maximum number of
+     * notifications that a client will fetch from its server. The
      * value associated with this attribute should be an
-     * <code>Integer</code> object.  The default value is 1000.</p>
+     * {@code Integer} object.  The default value is 1000.
      */
     public static final String MAX_FETCH_NOTIFS =
         "jmx.remote.x.notification.fetch.max";
@@ -334,10 +333,10 @@
     }
 
     /**
-     * <p>Name of the attribute that specifies the timeout for a
+     * Name of the attribute that specifies the timeout for a
      * client to fetch notifications from its server. The value
      * associated with this attribute should be a <code>Long</code>
-     * object.  The default value is 60000 milliseconds.</p>
+     * object.  The default value is 60000 milliseconds.
      */
     public static final String FETCH_TIMEOUT =
         "jmx.remote.x.notification.fetch.timeout";
@@ -351,11 +350,12 @@
     }
 
     /**
-     * <p>Name of the attribute that specifies an object that will check
+     * Name of the attribute that specifies an object that will check
      * accesses to add/removeNotificationListener and also attempts to
      * receive notifications.  The value associated with this attribute
      * should be a <code>NotificationAccessController</code> object.
-     * The default value is null.</p>
+     * The default value is null.
+     * <p>
      * This field is not public because of its com.sun dependency.
      */
     public static final String NOTIF_ACCESS_CONTROLLER =
@@ -630,9 +630,9 @@
     }
 
     /**
-     * <p>Name of the attribute that specifies the timeout to keep a
+     * Name of the attribute that specifies the timeout to keep a
      * server side connection after answering last client request.
-     * The default value is 120000 milliseconds.</p>
+     * The default value is 120000 milliseconds.
      */
     public static final String SERVER_CONNECTION_TIMEOUT =
         "jmx.remote.x.server.connection.timeout";
@@ -646,9 +646,9 @@
     }
 
     /**
-     * <p>Name of the attribute that specifies the period in
-     * millisecond for a client to check its connection.  The default
-     * value is 60000 milliseconds.</p>
+     * Name of the attribute that specifies the period in
+     * millisecond for a client to check its connection. The default
+     * value is 60000 milliseconds.
      */
     public static final String CLIENT_CONNECTION_CHECK_PERIOD =
         "jmx.remote.x.client.connection.check.period";
@@ -741,13 +741,13 @@
     }
 
     /**
-     * <p>Name of the attribute that specifies whether a connector server
+     * Name of the attribute that specifies whether a connector server
      * should not prevent the VM from exiting
      */
     public static final String JMX_SERVER_DAEMON = "jmx.remote.x.daemon";
 
     /**
-     * Returns true if {@value SERVER_DAEMON} is specified in the {@code env}
+     * Returns true if {@value JMX_SERVER_DAEMON} is specified in the {@code env}
      * as a key and its value is a String and it is equal to true ignoring case.
      *
      * @param env
--- a/jdk/src/java.management/share/classes/javax/management/package.html	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.management/share/classes/javax/management/package.html	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
         <p>Provides the core classes for the Java Management Extensions.</p>
 
         <p>The Java Management Extensions
-            (JMX<sup><font size="-1">TM</font></sup>) API is a standard
+            (JMX&trade;) API is a standard
         API for management and monitoring.  Typical uses include:</p>
 
         <ul>
@@ -87,8 +87,7 @@
             notion of <em>Standard MBeans</em>.  A Standard MBean is one
             whose attributes and operations are deduced from a Java
             interface using certain naming patterns, similar to those used
-            by JavaBeans<sup><font size="-1">TM</font></sup>.  For
-        example, consider an interface like this:</p>
+            by JavaBeans&trade;.  For example, consider an interface like this:</p>
 
         <pre>
     public interface ConfigurationMBean {
--- a/jdk/src/java.management/share/classes/javax/management/remote/package.html	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.management/share/classes/javax/management/remote/package.html	Wed Jul 05 20:35:10 2017 +0200
@@ -1,6 +1,6 @@
 <html>
 <head>
-    <title>JMX<sup><font size="-2">TM</font></sup> Remote API.</title>
+    <title>JMX&trade; Remote API.</title>
 <!--
 Copyright (c) 2002, 2014, Oracle and/or its affiliates. All rights reserved.
 DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
--- a/jdk/src/java.management/share/classes/javax/management/remote/rmi/package.html	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.management/share/classes/javax/management/remote/rmi/package.html	Wed Jul 05 20:35:10 2017 +0200
@@ -387,12 +387,11 @@
 
  
     @see <a href="{@docRoot}/../technotes/guides/rmi/index.html">
-	Java<sup><font size="-1">TM</font></sup> Remote Method
+	Java&trade; Remote Method
 	Invocation (RMI)</a>
 
     @see <a href="{@docRoot}/../technotes/guides/jndi/index.html">
-	Java Naming and Directory Interface<sup><font
-	size="-1">TM</font></sup> (JNDI)</a>
+	Java Naming and Directory Interface&trade; (JNDI)</a>
 
     @see <a href="http://www.ietf.org/rfc/rfc2045.txt">RFC 2045,
     section 6.8, "Base64 Content-Transfer-Encoding"</a>
--- a/jdk/src/java.management/share/classes/sun/management/HotspotRuntimeMBean.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.management/share/classes/sun/management/HotspotRuntimeMBean.java	Wed Jul 05 20:35:10 2017 +0200
@@ -64,7 +64,7 @@
      * Returns a list of internal counters maintained in the Java
      * virtual machine for the runtime system.
      *
-     * @return a <tt>List</tt> of internal counters maintained in the VM
+     * @return a {@code List} of internal counters maintained in the VM
      * for the runtime system.
      */
     public java.util.List<Counter> getInternalRuntimeCounters();
--- a/jdk/src/java.management/share/classes/sun/management/HotspotThreadMBean.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.management/share/classes/sun/management/HotspotThreadMBean.java	Wed Jul 05 20:35:10 2017 +0200
@@ -40,12 +40,11 @@
     public int getInternalThreadCount();
 
     /**
-     * Returns a <tt>Map</tt> of the name of all VM internal threads
+     * Returns a {@code Map} of the name of all VM internal threads
      * to the thread CPU time in nanoseconds.  The returned value is
      * of nanoseconds precision but not necessarily nanoseconds accuracy.
-     * <p>
      *
-     * @return a <tt>Map</tt> object of the name of all VM internal threads
+     * @return a {@code Map} object of the name of all VM internal threads
      * to the thread CPU time in nanoseconds.
      *
      * @throws java.lang.UnsupportedOperationException if the Java virtual
--- a/jdk/src/java.management/share/classes/sun/management/MappedMXBeanType.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.management/share/classes/sun/management/MappedMXBeanType.java	Wed Jul 05 20:35:10 2017 +0200
@@ -45,13 +45,15 @@
  * A mapped mxbean type maps a Java type to an open type.
  * Only the following Java types are mappable
  * (currently required by the platform MXBeans):
- *   1. Primitive types
- *   2. Wrapper classes such java.lang.Integer, etc
- *   3. Classes with only getter methods and with a static "from" method
- *      that takes a CompositeData argument.
- *   4. E[] where E is a type of 1-4 (can be multi-dimensional array)
- *   5. List<E> where E is a type of 1-3
- *   6. Map<K, V> where K and V are a type of 1-4
+ * <ol>
+ *   <li>Primitive types</li>
+ *   <li>Wrapper classes such java.lang.Integer, etc</li>
+ *   <li>Classes with only getter methods and with a static "from" method
+ *      that takes a CompositeData argument.</li>
+ *   <li>{@code E[]} where {@code E} is a type of 1-4 (can be multi-dimensional array)</li>
+ *   <li>{@code List<E>} where E is a type of 1-3</li>
+ *   <li>{@code Map<K, V>} where {@code K} and {@code V} are a type of 1-4</li>
+ * </ol>
  *
  * OpenDataException will be thrown if a Java type is not supported.
  */
--- a/jdk/src/java.management/share/classes/sun/management/Sensor.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.management/share/classes/sun/management/Sensor.java	Wed Jul 05 20:35:10 2017 +0200
@@ -34,12 +34,12 @@
  * An abstract sensor.
  *
  * <p>
- * A <tt>AbstractSensor</tt> object consists of two attributes:
+ * A {@code AbstractSensor} object consists of two attributes:
  * <ul>
- *   <li><tt>on</tt> is a boolean flag indicating if a sensor is
+ *   <li>{@code on} is a boolean flag indicating if a sensor is
  *       triggered. This flag will be set or cleared by the
  *       component that owns the sensor.</li>
- *   <li><tt>count</tt> is the total number of times that a sensor
+ *   <li>{@code count} is the total number of times that a sensor
  *       has been triggered.</li>
  * </ul>
  *
@@ -54,7 +54,7 @@
     private boolean on;
 
     /**
-     * Constructs a <tt>Sensor</tt> object.
+     * Constructs a {@code Sensor} object.
      *
      * @param name The name of this sensor.
      */
@@ -88,8 +88,8 @@
     /**
      * Tests if this sensor is currently on.
      *
-     * @return <tt>true</tt> if the sensor is currently on;
-     *         <tt>false</tt> otherwise.
+     * @return {@code true} if the sensor is currently on;
+     *         {@code false} otherwise.
      *
      */
     public boolean isOn() {
@@ -112,7 +112,7 @@
 
     /**
      * Triggers this sensor. This method sets this sensor on
-     * and increments the count with the input <tt>increment</tt>.
+     * and increments the count with the input {@code increment}.
      */
     public void trigger(int increment) {
         synchronized (lock) {
@@ -126,7 +126,7 @@
     /**
      * Triggers this sensor piggybacking a memory usage object.
      * This method sets this sensor on
-     * and increments the count with the input <tt>increment</tt>.
+     * and increments the count with the input {@code increment}.
      */
     public void trigger(int increment, MemoryUsage usage) {
         synchronized (lock) {
@@ -150,7 +150,7 @@
 
     /**
      * Clears this sensor
-     * and increments the count with the input <tt>increment</tt>.
+     * and increments the count with the input {@code increment}.
      */
     public void clear(int increment) {
         synchronized (lock) {
--- a/jdk/src/java.management/share/classes/sun/management/counter/Counter.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.management/share/classes/sun/management/counter/Counter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -63,7 +63,7 @@
     public Object getValue();
 
     /**
-     * Returns <tt>true</tt> if this counter is an internal counter.
+     * Returns {@code true} if this counter is an internal counter.
      */
     public boolean isInternal();
 
--- a/jdk/src/java.management/share/classes/sun/management/counter/perf/InstrumentationException.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.management/share/classes/sun/management/counter/perf/InstrumentationException.java	Wed Jul 05 20:35:10 2017 +0200
@@ -27,14 +27,14 @@
 
 public class InstrumentationException extends RuntimeException {
     /**
-     * Constructs a <tt>InstrumentationException</tt> with no
+     * Constructs a {@code InstrumentationException} with no
      * detail message.
      */
      public InstrumentationException() {
      }
 
     /**
-     * Constructs a <tt>InstrumentationException</tt> with a specified
+     * Constructs a {@code InstrumentationException} with a specified
      * detail message.
      *
      * @param message the detail message
--- a/jdk/src/java.management/share/classes/sun/management/jdp/JdpController.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.management/share/classes/sun/management/jdp/JdpController.java	Wed Jul 05 20:35:10 2017 +0200
@@ -37,19 +37,18 @@
 import sun.misc.ManagedLocalsThread;
 
 /**
- * JdpController is responsible to create and manage a broadcast loop
+ * JdpController is responsible to create and manage a broadcast loop.
  *
  * <p> Other part of code has no access to broadcast loop and have to use
  * provided static methods
  * {@link #startDiscoveryService(InetAddress,int,String,String) startDiscoveryService}
- * and {@link #stopDiscoveryService() stopDiscoveryService}</p>
+ * and {@link #stopDiscoveryService() stopDiscoveryService}
  * <p>{@link #startDiscoveryService(InetAddress,int,String,String) startDiscoveryService} could be called multiple
- * times as it stops the running service if it is necessary. Call to {@link #stopDiscoveryService() stopDiscoveryService}
- * ignored if service isn't run</p>
+ * times as it stops the running service if it is necessary.
+ * Call to {@link #stopDiscoveryService() stopDiscoveryService}
+ * ignored if service isn't run.
  *
  *
- * </p>
- *
  * <p> System properties below could be used to control broadcast loop behavior.
  * Property below have to be set explicitly in command line. It's not possible to
  * set it in management.config file.  Careless changes of these properties could
@@ -59,9 +58,9 @@
  *     <li>com.sun.management.jdp.pause       - set broadcast interval in seconds</li>
  *     <li>com.sun.management.jdp.source_addr - an address of interface to use for broadcast</li>
  * </ul>
-  </p>
+ *
  * <p>null parameters values are filtered out on {@link JdpPacketWriter} level and
- * corresponding keys are not placed to packet.</p>
+ * corresponding keys are not placed to packet.
  */
 public final class JdpController {
 
--- a/jdk/src/java.naming/share/classes/com/sun/jndi/ldap/BasicControl.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.naming/share/classes/com/sun/jndi/ldap/BasicControl.java	Wed Jul 05 20:35:10 2017 +0200
@@ -28,7 +28,7 @@
 import javax.naming.ldap.*;
 
 /**
-  * This class provides a basic implementation of the <tt>Control</tt>
+  * This class provides a basic implementation of the {@code Control}
   * interface. It represents an LDAPv3 Control as defined in RFC-2251.
   *
   * @author Vincent Ryan
--- a/jdk/src/java.naming/share/classes/com/sun/jndi/ldap/BerDecoder.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.naming/share/classes/com/sun/jndi/ldap/BerDecoder.java	Wed Jul 05 20:35:10 2017 +0200
@@ -295,7 +295,7 @@
      *          the relative parsed position is not returned.
      * @return A non-null array containing the octet string.
      * @throws DecodeException If the next byte in the BER buffer is not
-     * <tt>tag</tt>, or if length specified in the BER buffer exceeds the
+     * {@code tag}, or if length specified in the BER buffer exceeds the
      * number of bytes left in the buffer.
      */
     public byte[] parseOctetString(int tag, int rlen[]) throws DecodeException {
--- a/jdk/src/java.naming/share/classes/com/sun/jndi/ldap/EventQueue.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.naming/share/classes/com/sun/jndi/ldap/EventQueue.java	Wed Jul 05 20:35:10 2017 +0200
@@ -73,16 +73,16 @@
     // package private;
     /**
      * Enqueue an event.
-     * @param event Either a <tt>NamingExceptionEvent</tt> or a subclass
-     *              of <tt>NamingEvent</tt> or
-     * <tt>UnsolicitedNotificationEvent</tt>.
-     * If it is a subclass of <tt>NamingEvent</tt>, all listeners must implement
-     * the corresponding subinterface of <tt>NamingListener</tt>.
-     * For example, for a <tt>ObjectAddedEvent</tt>, all listeners <em>must</em>
-     * implement the <tt>ObjectAddedListener</tt> interface.
+     * @param event Either a {@code NamingExceptionEvent} or a subclass
+     *        of {@code NamingEvent} or
+     *        {@code UnsolicitedNotificationEvent}.
+     * If it is a subclass of {@code NamingEvent}, all listeners must implement
+     * the corresponding subinterface of {@code NamingListener}.
+     * For example, for a {@code ObjectAddedEvent}, all listeners <em>must</em>
+     * implement the {@code ObjectAddedListener} interface.
      * <em>The current implementation does not check this before dispatching
      * the event.</em>
-     * If the event is a <tt>NamingExceptionEvent</tt>, then all listeners
+     * If the event is a {@code NamingExceptionEvent}, then all listeners
      * are notified.
      * @param vector List of NamingListeners that will be notified of event.
      */
--- a/jdk/src/java.naming/share/classes/com/sun/jndi/ldap/EventSupport.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.naming/share/classes/com/sun/jndi/ldap/EventSupport.java	Wed Jul 05 20:35:10 2017 +0200
@@ -55,14 +55,14 @@
  *<li>The filter (default is "(objectclass=*)").
  *<li>The search controls (default is null SearchControls).
  *<li>The events that the listener is interested in. This is determined by
- * finding out which <tt>NamingListener</tt> interface the listener supports.
+ * finding out which {@code NamingListener} interface the listener supports.
  *</ul>
  *<p>
- *A notifier (<tt>NamingEventNotifier</tt>) is a worker thread that is responsible
+ *A notifier ({@code NamingEventNotifier}) is a worker thread that is responsible
  *for gathering information for generating events requested by its listeners.
  *Each notifier maintains its own list of listeners; these listeners have
  *all made the same registration request (at different times) and implements
- *the same <tt>NamingListener</tt> interfaces.
+ *the same {@code NamingListener} interfaces.
  *<p>
  *For unsolicited listeners, this class maintains a vector, unsolicited.
  *When an unsolicited listener is registered, this class adds itself
@@ -93,7 +93,7 @@
  *The notifiers are responsible for gather information for generating events
  *requested by their respective listeners. When a notifier gets sufficient
  *information to generate an event, it creates invokes the
- *appropriate <tt>fireXXXEvent</tt> on this class with the information and list of
+ *appropriate {@code fireXXXEvent} on this class with the information and list of
  *listeners. This causes an event and the list of listeners to be added
  *to the <em>event queue</em>.
  *This class maintains an event queue and a dispatching thread that dequeues
@@ -138,7 +138,7 @@
     }
 
     /**
-     * Adds <tt>l</tt> to list of listeners interested in <tt>nm</tt>.
+     * Adds {@code l} to list of listeners interested in {@code nm}.
      */
     /*
      * Make the add/removeNamingListeners synchronized to:
@@ -173,7 +173,7 @@
     }
 
     /**
-     * Adds <tt>l</tt> to list of listeners interested in <tt>nm</tt>
+     * Adds {@code l} to list of listeners interested in {@code nm}
      * and filter.
      */
     synchronized void addNamingListener(String nm, String filter,
@@ -201,7 +201,7 @@
     }
 
     /**
-     * Removes <tt>l</tt> from all notifiers in this context.
+     * Removes {@code l} from all notifiers in this context.
      */
     synchronized void removeNamingListener(NamingListener l) {
         if (debug) System.err.println("EventSupport removing listener");
--- a/jdk/src/java.naming/share/classes/com/sun/jndi/ldap/LdapName.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.naming/share/classes/com/sun/jndi/ldap/LdapName.java	Wed Jul 05 20:35:10 2017 +0200
@@ -336,7 +336,7 @@
      * characters:
      *<ul>
      *<li>leading and trailing whitespace
-     *<li><pre>, = + < > # ; " \</pre>
+     *<li><pre>{@literal , = + < > # ; " \}</pre>
      *</ul>
      * If the value is a byte array, it is converted to hex
      * notation (such as "#CEB1DF80").
--- a/jdk/src/java.naming/share/classes/com/sun/jndi/ldap/LdapReferralException.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.naming/share/classes/com/sun/jndi/ldap/LdapReferralException.java	Wed Jul 05 20:35:10 2017 +0200
@@ -35,7 +35,7 @@
   * This exception is raised when a referral to an alternative context
   * is encountered.
   * <p>
-  * An <tt>LdapReferralException</tt> object contains one or more referrals.
+  * An {@code LdapReferralException} object contains one or more referrals.
   * Each referral is an alternative location for the same target entry.
   * For example, a referral may be an LDAP URL.
   * The referrals are attempted in sequence until one is successful or
@@ -46,20 +46,20 @@
   * of an authentication error, a referral may be retried with different
   * environment properties.
   * <p>
-  * An <tt>LdapReferralException</tt> object may also contain a reference
-  * to a chain of unprocessed <tt>LdapReferralException</tt> objects.
+  * An {@code LdapReferralException} object may also contain a reference
+  * to a chain of unprocessed {@code LdapReferralException} objects.
   * Once the current set of referrals have been exhausted and unprocessed
-  * <tt>LdapReferralException</tt> objects remain, then the
-  * <tt>LdapReferralException</tt> object referenced by the current
+  * {@code LdapReferralException} objects remain, then the
+  * {@code LdapReferralException} object referenced by the current
   * object is thrown and the cycle continues.
   * <p>
-  * If new <tt>LdapReferralException</tt> objects are generated while
+  * If new {@code LdapReferralException} objects are generated while
   * following an existing referral then these new objects are appended
-  * to the end of the chain of unprocessed <tt>LdapReferralException</tt>
+  * to the end of the chain of unprocessed {@code LdapReferralException}
   * objects.
   * <p>
   * If an exception was recorded while processing a chain of
-  * <tt>LdapReferralException</tt> objects then it is throw once
+  * {@code LdapReferralException} objects then it is throw once
   * processing has completed.
   *
   * @author Vincent Ryan
--- a/jdk/src/java.naming/share/classes/com/sun/jndi/ldap/UnsolicitedResponseImpl.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.naming/share/classes/com/sun/jndi/ldap/UnsolicitedResponseImpl.java	Wed Jul 05 20:35:10 2017 +0200
@@ -65,7 +65,7 @@
       * Retrieves the object identifier of the response.
       *
       * @return A possibly null object identifier string representing the LDAP
-      *         <tt>ExtendedResponse.responseName</tt> component.
+      *         {@code ExtendedResponse.responseName} component.
       */
     public String getID() {
         return oid;
@@ -79,7 +79,7 @@
       * the response value. It does not include the response OID.
       *
       * @return A possibly null byte array representing the ASN.1 BER encoded
-      *         contents of the LDAP <tt>ExtendedResponse.response</tt>
+      *         contents of the LDAP {@code ExtendedResponse.response}
       *         component.
       */
     public byte[] getEncodedValue() {
--- a/jdk/src/java.naming/share/classes/com/sun/jndi/ldap/ext/StartTlsResponseImpl.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.naming/share/classes/com/sun/jndi/ldap/ext/StartTlsResponseImpl.java	Wed Jul 05 20:35:10 2017 +0200
@@ -52,10 +52,10 @@
  * The object identifier for StartTLS is 1.3.6.1.4.1.1466.20037
  * and no extended response value is defined.
  *
- *<p>
+ * <p>
  * The Start TLS extended request and response are used to establish
  * a TLS connection over the existing LDAP connection associated with
- * the JNDI context on which <tt>extendedOperation()</tt> is invoked.
+ * the JNDI context on which {@code extendedOperation()} is invoked.
  *
  * @see StartTlsRequest
  * @author Vincent Ryan
@@ -124,7 +124,7 @@
     /**
      * Overrides the default list of cipher suites enabled for use on the
      * TLS connection. The cipher suites must have already been listed by
-     * <tt>SSLSocketFactory.getSupportedCipherSuites()</tt> as being supported.
+     * {@code SSLSocketFactory.getSupportedCipherSuites()} as being supported.
      * Even if a suite has been enabled, it still might not be used because
      * the peer does not support it, or because the requisite certificates
      * (and private keys) are not available.
@@ -140,12 +140,12 @@
     }
 
     /**
-     * Overrides the default hostname verifier used by <tt>negotiate()</tt>
+     * Overrides the default hostname verifier used by {@code negotiate()}
      * after the TLS handshake has completed. If
-     * <tt>setHostnameVerifier()</tt> has not been called before
-     * <tt>negotiate()</tt> is invoked, <tt>negotiate()</tt>
+     * {@code setHostnameVerifier()} has not been called before
+     * {@code negotiate()} is invoked, {@code negotiate()}
      * will perform a simple case ignore match. If called after
-     * <tt>negotiate()</tt>, this method does not do anything.
+     * {@code negotiate()}, this method does not do anything.
      *
      * @param verifier The non-null hostname verifier callback.
      * @see #negotiate
@@ -157,10 +157,10 @@
     /**
      * Negotiates a TLS session using the default SSL socket factory.
      * <p>
-     * This method is equivalent to <tt>negotiate(null)</tt>.
+     * This method is equivalent to {@code negotiate(null)}.
      *
      * @return The negotiated SSL session
-     * @throw IOException If an IO error was encountered while establishing
+     * @throws IOException If an IO error was encountered while establishing
      * the TLS session.
      * @see #setEnabledCipherSuites
      * @see #setHostnameVerifier
@@ -177,7 +177,7 @@
      * attaches it to the existing connection. Performs the TLS handshake
      * and returns the negotiated session information.
      * <p>
-     * If cipher suites have been set via <tt>setEnabledCipherSuites</tt>
+     * If cipher suites have been set via {@code setEnabledCipherSuites}
      * then they are enabled before the TLS handshake begins.
      * <p>
      * Hostname verification is performed after the TLS handshake completes.
@@ -186,7 +186,7 @@
      * hostname is extracted from the subjectAltName in the server's
      * certificate (if present). Otherwise the value of the common name
      * attribute of the subject name is used. If a callback has
-     * been set via <tt>setHostnameVerifier</tt> then that verifier is used if
+     * been set via {@code setHostnameVerifier} then that verifier is used if
      * the default check fails.
      * <p>
      * If an error occurs then the SSL socket is closed and an IOException
@@ -195,7 +195,7 @@
      * @param factory The possibly null SSL socket factory to use.
      * If null, the default SSL socket factory is used.
      * @return The negotiated SSL session
-     * @throw IOException If an IO error was encountered while establishing
+     * @throws IOException If an IO error was encountered while establishing
      * the TLS session.
      * @see #setEnabledCipherSuites
      * @see #setHostnameVerifier
@@ -252,7 +252,7 @@
      * Closes the TLS connection gracefully and reverts back to the underlying
      * connection.
      *
-     * @throw IOException If an IO error was encountered while closing the
+     * @throws IOException If an IO error was encountered while closing the
      * TLS connection
      */
     public void close() throws IOException {
--- a/jdk/src/java.naming/share/classes/com/sun/jndi/ldap/sasl/LdapSasl.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.naming/share/classes/com/sun/jndi/ldap/sasl/LdapSasl.java	Wed Jul 05 20:35:10 2017 +0200
@@ -72,12 +72,12 @@
      * property has not been set, Context.SECURITY_PRINCIPAL is used.
      * If SASL_CALLBACK has been set, use that instead of the default
      * CallbackHandler.
-     *<p>
+     * <p>
      * If bind is successful and the selected SASL mechanism has a security
      * layer, set inStream and outStream to be filter streams that use
      * the security layer. These will be used for subsequent communication
      * with the server.
-     *<p>
+     *
      * @param conn The non-null connection to use for sending an LDAP BIND
      * @param server Non-null string name of host to connect to
      * @param dn Non-null DN to bind as; also used as authentication ID
--- a/jdk/src/java.naming/share/classes/com/sun/jndi/toolkit/ctx/Continuation.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.naming/share/classes/com/sun/jndi/toolkit/ctx/Continuation.java	Wed Jul 05 20:35:10 2017 +0200
@@ -329,7 +329,7 @@
      *<p>
      * After this method is called, isContinuing() returns true.
      *
-     * @param resObj The possibly null resolved object.
+     * @param obj The possibly null resolved object.
      * @param relResName The non-null resolved name relative to currCtx.
      * @param currCtx The non-null context from which relResName is to be resolved.
      */
@@ -349,7 +349,7 @@
      *<p>
      * After this method is called, isContinuing() returns true.
      *
-     * @param resObj The possibly null resolved object.
+     * @param obj The possibly null resolved object.
      * @param relResName The non-null resolved name relative to currCtx.
      * @param currCtx The non-null context from which relResName is to be resolved.
      * @param remain The non-null remaining name.
@@ -366,7 +366,7 @@
     /**
      * String overload.
      *
-     * @param resObj The possibly null resolved object.
+     * @param obj The possibly null resolved object.
      * @param relResName The non-null resolved name relative to currCtx.
      * @param currCtx The non-null context from which relResName is to be resolved.
      * @param remain The non-null remaining name.
--- a/jdk/src/java.naming/share/classes/com/sun/jndi/toolkit/ctx/PartialCompositeContext.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.naming/share/classes/com/sun/jndi/toolkit/ctx/PartialCompositeContext.java	Wed Jul 05 20:35:10 2017 +0200
@@ -452,14 +452,14 @@
      * nonempty component, and if 'prefix' ends with an empty component or
      * 'name' starts with one, then one empty component is dropped.
      * For example:
-     * <pre>
+     * <pre>{@code
      *                            elideEmpty=false     elideEmpty=true
      * {"a"} + {"b"}          =>  {"a", "b"}           {"a", "b"}
      * {"a"} + {""}           =>  {"a", ""}            {"a", ""}
      * {"a"} + {"", "b"}      =>  {"a", "", "b"}       {"a", "b"}
      * {"a", ""} + {"b", ""}  =>  {"a", "", "b", ""}   {"a", "b", ""}
      * {"a", ""} + {"", "b"}  =>  {"a", "", "", "b"}   {"a", "", "b"}
-     * </pre>
+     * }</pre>
      */
     public Name composeName(Name name, Name prefix) throws NamingException {
         Name res = (Name)prefix.clone();
--- a/jdk/src/java.naming/share/classes/com/sun/jndi/toolkit/dir/HierMemDirCtx.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.naming/share/classes/com/sun/jndi/toolkit/dir/HierMemDirCtx.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,8 +32,8 @@
 /**
  * A sample service provider that implements a hierarchical directory in memory.
  * Every operation begins by doing a lookup on the name passed to it and then
- * calls a corresponding "do<OperationName>" on the result of the lookup. The
- * "do<OperationName>" does the work without any further resolution (it assumes
+ * calls a corresponding "{@code do<OperationName>}" on the result of the lookup. The
+ * "{@code do<OperationName>}" does the work without any further resolution (it assumes
  * that it is the target context).
  */
 
--- a/jdk/src/java.naming/share/classes/com/sun/jndi/toolkit/dir/SearchFilter.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.naming/share/classes/com/sun/jndi/toolkit/dir/SearchFilter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -548,8 +548,8 @@
 
 
     /**
-      * Finds the first occurrence of <tt>ch</tt> in <tt>val</tt> starting
-      * from position <tt>start</tt>. It doesn't count if <tt>ch</tt>
+      * Finds the first occurrence of {@code ch} in {@code val} starting
+      * from position {@code start}. It doesn't count if {@code ch}
       * has been escaped by a backslash (\)
       */
     public static int findUnescaped(char ch, String val, int start) {
@@ -568,8 +568,8 @@
     }
 
     /**
-     * Formats the expression <tt>expr</tt> using arguments from the array
-     * <tt>args</tt>.
+     * Formats the expression {@code expr} using arguments from the array
+     * {@code args}.
      *
      * <code>{i}</code> specifies the <code>i</code>'th element from
      * the array <code>args</code> is to be substituted for the
--- a/jdk/src/java.naming/share/classes/com/sun/jndi/toolkit/url/GenericURLContext.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.naming/share/classes/com/sun/jndi/toolkit/url/GenericURLContext.java	Wed Jul 05 20:35:10 2017 +0200
@@ -107,12 +107,14 @@
       * the subclass must override getURLSuffix() to get the correct behavior.
       * Remember, the behavior must match getRootURLContext().
       *
+      * <pre>{@code
       * URL                                     Suffix
       * foo://host:port                         <empty string>
       * foo://host:port/rest/of/name            rest/of/name
       * foo:///rest/of/name                     rest/of/name
       * foo:/rest/of/name                       rest/of/name
       * foo:rest/of/name                        rest/of/name
+      * }</pre>
       */
     protected Name getURLSuffix(String prefix, String url) throws NamingException {
         String suffix = url.substring(prefix.length());
--- a/jdk/src/java.naming/share/classes/com/sun/jndi/toolkit/url/Uri.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.naming/share/classes/com/sun/jndi/toolkit/url/Uri.java	Wed Jul 05 20:35:10 2017 +0200
@@ -47,7 +47,7 @@
  * still run on pre-1.4 platforms not containing that class.
  *
  * <p> The format of an absolute URI (see the RFCs mentioned above) is:
- * <p><blockquote><pre>
+ * <blockquote><pre>{@code
  *      absoluteURI   = scheme ":" ( hier_part | opaque_part )
  *
  *      scheme        = alpha *( alpha | digit | "+" | "-" | "." )
@@ -94,12 +94,12 @@
  *      mark          = "-" | "_" | "." | "!" | "~" | "*" | "'" | "(" | ")"
  *      escaped       = "%" hex hex
  *      unwise        = "{" | "}" | "|" | "\" | "^" | "`"
- * </pre></blockquote>
+ * }</pre></blockquote>
  *
- * <p> Currently URIs containing <tt>userinfo</tt> or <tt>reg_name</tt>
+ * <p> Currently URIs containing {@code userinfo} or {@code reg_name}
  * are not supported.
- * The <tt>opaque_part</tt> of a non-hierarchical URI is treated as if
- * if were a <tt>path</tt> without a leading slash.
+ * The {@code opaque_part} of a non-hierarchical URI is treated as if
+ * if were a {@code path} without a leading slash.
  */
 
 
--- a/jdk/src/java.naming/share/classes/javax/naming/directory/package.html	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.naming/share/classes/javax/naming/directory/package.html	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
 
 <p>
 This package defines the directory operations of the Java Naming and
-Directory Interface<font size=-2><sup>TM</sup></font> (JNDI). &nbsp;
+Directory Interface&trade; (JNDI). &nbsp;
 JNDI provides naming and directory functionality to applications
 written in the Java programming language.  It is designed to be
 independent of any specific naming or directory service
--- a/jdk/src/java.naming/share/classes/javax/naming/event/package.html	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.naming/share/classes/javax/naming/event/package.html	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
 
 <p>
 This package defines the event notification operations of the Java Naming
-and Directory Interface<font size=-2><sup>TM</sup></font> (JNDI). &nbsp;
+and Directory Interface&trade; (JNDI). &nbsp;
 JNDI provides naming and directory functionality to applications
 written in the Java programming language.  It is designed to be
 independent of any specific naming or directory service
--- a/jdk/src/java.naming/share/classes/javax/naming/ldap/package.html	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.naming/share/classes/javax/naming/ldap/package.html	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
 
 <p>
 This package extends the directory operations of the Java Naming and
-Directory Interface<font size=-2><sup>TM</sup></font> (JNDI). &nbsp;
+Directory Interface&trade; (JNDI). &nbsp;
 JNDI provides naming and directory functionality to applications
 written in the Java programming language.  It is designed to be
 independent of any specific naming or directory service
--- a/jdk/src/java.naming/share/classes/javax/naming/package.html	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.naming/share/classes/javax/naming/package.html	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,7 @@
 
 <p>
 This package defines the naming operations of the Java Naming and
-Directory Interface<font size=-2><sup>TM</sup></font> (JNDI). &nbsp;
+Directory Interface&trade; (JNDI). &nbsp;
 JNDI provides naming and directory functionality to applications
 written in the Java programming language.  It is designed to be
 independent of any specific naming or directory service
--- a/jdk/src/java.naming/share/classes/javax/naming/spi/package.html	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.naming/share/classes/javax/naming/spi/package.html	Wed Jul 05 20:35:10 2017 +0200
@@ -34,7 +34,7 @@
 
 <p>
 This package defines the service provider interface (SPI) of the Java Naming
-and Directory Interface<font size=-2><sup>TM</sup></font> (JNDI). &nbsp;
+and Directory Interface&trade; (JNDI). &nbsp;
 JNDI provides naming and directory functionality to applications
 written in the Java programming language.  It is designed to be
 independent of any specific naming or directory service
--- a/jdk/src/java.prefs/windows/classes/java/util/prefs/WindowsPreferences.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.prefs/windows/classes/java/util/prefs/WindowsPreferences.java	Wed Jul 05 20:35:10 2017 +0200
@@ -62,8 +62,8 @@
     /**
      * Windows registry path to <tt>Preferences</tt>'s root nodes.
      */
-    private static final byte[] WINDOWS_ROOT_PATH
-                               = stringToByteArray("Software\\JavaSoft\\Prefs");
+    private static final byte[] WINDOWS_ROOT_PATH =
+        stringToByteArray("Software\\JavaSoft\\Prefs");
 
     /**
      * Windows handles to <tt>HKEY_CURRENT_USER</tt> and
@@ -147,12 +147,12 @@
      * Java wrapper for Windows registry API RegOpenKey()
      */
     private static native int[] WindowsRegOpenKey(int hKey, byte[] subKey,
-                                                         int securityMask);
+                                                  int securityMask);
     /**
      * Retries RegOpenKey() MAX_ATTEMPTS times before giving up.
      */
     private static int[] WindowsRegOpenKey1(int hKey, byte[] subKey,
-                                                      int securityMask) {
+                                            int securityMask) {
         int[] result = WindowsRegOpenKey(hKey, subKey, securityMask);
         if (result[ERROR_CODE] == ERROR_SUCCESS) {
             return result;
@@ -167,16 +167,16 @@
         } else if (result[ERROR_CODE] != ERROR_ACCESS_DENIED) {
             long sleepTime = INIT_SLEEP_TIME;
             for (int i = 0; i < MAX_ATTEMPTS; i++) {
-            try {
-                Thread.sleep(sleepTime);
-            } catch(InterruptedException e) {
-                return result;
-            }
-            sleepTime *= 2;
-            result = WindowsRegOpenKey(hKey, subKey, securityMask);
-            if (result[ERROR_CODE] == ERROR_SUCCESS) {
-                return result;
-            }
+                try {
+                    Thread.sleep(sleepTime);
+                } catch(InterruptedException e) {
+                    return result;
+                }
+                sleepTime *= 2;
+                result = WindowsRegOpenKey(hKey, subKey, securityMask);
+                if (result[ERROR_CODE] == ERROR_SUCCESS) {
+                    return result;
+                }
             }
         }
         return result;
@@ -198,10 +198,10 @@
     private static int[] WindowsRegCreateKeyEx1(int hKey, byte[] subKey) {
         int[] result = WindowsRegCreateKeyEx(hKey, subKey);
         if (result[ERROR_CODE] == ERROR_SUCCESS) {
-                return result;
-            } else {
-                long sleepTime = INIT_SLEEP_TIME;
-                for (int i = 0; i < MAX_ATTEMPTS; i++) {
+            return result;
+        } else {
+            long sleepTime = INIT_SLEEP_TIME;
+            for (int i = 0; i < MAX_ATTEMPTS; i++) {
                 try {
                     Thread.sleep(sleepTime);
                 } catch(InterruptedException e) {
@@ -210,7 +210,7 @@
                 sleepTime *= 2;
                 result = WindowsRegCreateKeyEx(hKey, subKey);
                 if (result[ERROR_CODE] == ERROR_SUCCESS) {
-                return result;
+                    return result;
                 }
             }
         }
@@ -232,10 +232,10 @@
     private static int WindowsRegFlushKey1(int hKey) {
         int result = WindowsRegFlushKey(hKey);
         if (result == ERROR_SUCCESS) {
-                return result;
-            } else {
-                long sleepTime = INIT_SLEEP_TIME;
-                for (int i = 0; i < MAX_ATTEMPTS; i++) {
+            return result;
+        } else {
+            long sleepTime = INIT_SLEEP_TIME;
+            for (int i = 0; i < MAX_ATTEMPTS; i++) {
                 try {
                     Thread.sleep(sleepTime);
                 } catch(InterruptedException e) {
@@ -244,7 +244,7 @@
                 sleepTime *= 2;
                 result = WindowsRegFlushKey(hKey);
                 if (result == ERROR_SUCCESS) {
-                return result;
+                    return result;
                 }
             }
         }
@@ -255,23 +255,23 @@
      * Java wrapper for Windows registry API RegQueryValueEx()
      */
     private static native byte[] WindowsRegQueryValueEx(int hKey,
-                                                              byte[] valueName);
+                                                        byte[] valueName);
     /**
      * Java wrapper for Windows registry API RegSetValueEx()
      */
     private static native int WindowsRegSetValueEx(int hKey, byte[] valueName,
-                                                         byte[] value);
+                                                   byte[] value);
     /**
      * Retries RegSetValueEx() MAX_ATTEMPTS times before giving up.
      */
     private static int WindowsRegSetValueEx1(int hKey, byte[] valueName,
-                                                         byte[] value) {
+                                             byte[] value) {
         int result = WindowsRegSetValueEx(hKey, valueName, value);
         if (result == ERROR_SUCCESS) {
-                return result;
-            } else {
-                long sleepTime = INIT_SLEEP_TIME;
-                for (int i = 0; i < MAX_ATTEMPTS; i++) {
+            return result;
+        } else {
+            long sleepTime = INIT_SLEEP_TIME;
+            for (int i = 0; i < MAX_ATTEMPTS; i++) {
                 try {
                     Thread.sleep(sleepTime);
                 } catch(InterruptedException e) {
@@ -280,7 +280,7 @@
                 sleepTime *= 2;
                 result = WindowsRegSetValueEx(hKey, valueName, value);
                 if (result == ERROR_SUCCESS) {
-                return result;
+                    return result;
                 }
             }
         }
@@ -303,10 +303,10 @@
     private static int[] WindowsRegQueryInfoKey1(int hKey) {
         int[] result = WindowsRegQueryInfoKey(hKey);
         if (result[ERROR_CODE] == ERROR_SUCCESS) {
-                return result;
-            } else {
-                long sleepTime = INIT_SLEEP_TIME;
-                for (int i = 0; i < MAX_ATTEMPTS; i++) {
+            return result;
+        } else {
+            long sleepTime = INIT_SLEEP_TIME;
+            for (int i = 0; i < MAX_ATTEMPTS; i++) {
                 try {
                     Thread.sleep(sleepTime);
                 } catch(InterruptedException e) {
@@ -315,7 +315,7 @@
                 sleepTime *= 2;
                 result = WindowsRegQueryInfoKey(hKey);
                 if (result[ERROR_CODE] == ERROR_SUCCESS) {
-                return result;
+                    return result;
                 }
             }
         }
@@ -326,19 +326,19 @@
      * Java wrapper for Windows registry API RegEnumKeyEx()
      */
     private static native byte[] WindowsRegEnumKeyEx(int hKey, int subKeyIndex,
-                                      int maxKeyLength);
+                                                     int maxKeyLength);
 
     /**
      * Retries RegEnumKeyEx() MAX_ATTEMPTS times before giving up.
      */
     private static byte[] WindowsRegEnumKeyEx1(int hKey, int subKeyIndex,
-                                      int maxKeyLength) {
+                                               int maxKeyLength) {
         byte[] result = WindowsRegEnumKeyEx(hKey, subKeyIndex, maxKeyLength);
         if (result != null) {
-                return result;
-            } else {
-                long sleepTime = INIT_SLEEP_TIME;
-                for (int i = 0; i < MAX_ATTEMPTS; i++) {
+            return result;
+        } else {
+            long sleepTime = INIT_SLEEP_TIME;
+            for (int i = 0; i < MAX_ATTEMPTS; i++) {
                 try {
                     Thread.sleep(sleepTime);
                 } catch(InterruptedException e) {
@@ -347,7 +347,7 @@
                 sleepTime *= 2;
                 result = WindowsRegEnumKeyEx(hKey, subKeyIndex, maxKeyLength);
                 if (result != null) {
-                return result;
+                    return result;
                 }
             }
         }
@@ -358,19 +358,19 @@
      * Java wrapper for Windows registry API RegEnumValue()
      */
     private static native byte[] WindowsRegEnumValue(int hKey, int valueIndex,
-                                      int maxValueNameLength);
+                                                     int maxValueNameLength);
     /**
      * Retries RegEnumValueEx() MAX_ATTEMPTS times before giving up.
      */
     private static byte[] WindowsRegEnumValue1(int hKey, int valueIndex,
-                                      int maxValueNameLength) {
+                                               int maxValueNameLength) {
         byte[] result = WindowsRegEnumValue(hKey, valueIndex,
-                                                            maxValueNameLength);
+                                            maxValueNameLength);
         if (result != null) {
-                return result;
-            } else {
-                long sleepTime = INIT_SLEEP_TIME;
-                for (int i = 0; i < MAX_ATTEMPTS; i++) {
+            return result;
+        } else {
+            long sleepTime = INIT_SLEEP_TIME;
+            for (int i = 0; i < MAX_ATTEMPTS; i++) {
                 try {
                     Thread.sleep(sleepTime);
                 } catch(InterruptedException e) {
@@ -378,9 +378,9 @@
                 }
                 sleepTime *= 2;
                 result = WindowsRegEnumValue(hKey, valueIndex,
-                                                            maxValueNameLength);
+                                             maxValueNameLength);
                 if (result != null) {
-                return result;
+                    return result;
                 }
             }
         }
@@ -404,11 +404,11 @@
         int[] result =
                WindowsRegCreateKeyEx1(parentNativeHandle, toWindowsName(name));
         if (result[ERROR_CODE] != ERROR_SUCCESS) {
-            logger().warning("Could not create windows registry "
-            + "node " + byteArrayToString(windowsAbsolutePath()) +
-            " at root 0x" + Integer.toHexString(rootNativeHandle()) +
-            ". Windows RegCreateKeyEx(...) returned error code " +
-            result[ERROR_CODE] + ".");
+            logger().warning("Could not create windows registry node " +
+                    byteArrayToString(windowsAbsolutePath()) +
+                    " at root 0x" + Integer.toHexString(rootNativeHandle()) +
+                    ". Windows RegCreateKeyEx(...) returned error code " +
+                    result[ERROR_CODE] + ".");
             isBackingStoreAvailable = false;
             return;
         }
@@ -426,15 +426,15 @@
      * @param rootDirectory Path to root directory, as a byte-encoded string.
      */
     private  WindowsPreferences(int rootNativeHandle, byte[] rootDirectory) {
-        super(null,"");
+        super(null, "");
         int[] result =
                 WindowsRegCreateKeyEx1(rootNativeHandle, rootDirectory);
         if (result[ERROR_CODE] != ERROR_SUCCESS) {
             logger().warning("Could not open/create prefs root node " +
-            byteArrayToString(windowsAbsolutePath()) + " at root 0x" +
-            Integer.toHexString(rootNativeHandle()) +
-            ". Windows RegCreateKeyEx(...) returned error code " +
-            result[ERROR_CODE] + ".");
+                    byteArrayToString(windowsAbsolutePath()) +
+                    " at root 0x" + Integer.toHexString(rootNativeHandle()) +
+                    ". Windows RegCreateKeyEx(...) returned error code " +
+                    result[ERROR_CODE] + ".");
             isBackingStoreAvailable = false;
             return;
         }
@@ -451,7 +451,7 @@
     private byte[] windowsAbsolutePath() {
         ByteArrayOutputStream bstream = new ByteArrayOutputStream();
         bstream.write(WINDOWS_ROOT_PATH, 0, WINDOWS_ROOT_PATH.length-1);
-        StringTokenizer tokenizer = new StringTokenizer(absolutePath(),"/");
+        StringTokenizer tokenizer = new StringTokenizer(absolutePath(), "/");
         while (tokenizer.hasMoreTokens()) {
             bstream.write((byte)'\\');
             String nextName = tokenizer.nextToken();
@@ -505,27 +505,30 @@
         /*  Check if key's path is short enough be opened at once
             otherwise use a path-splitting procedure */
         if (windowsAbsolutePath.length <= MAX_WINDOWS_PATH_LENGTH + 1) {
-             int[] result = WindowsRegOpenKey1(rootNativeHandle(),
-                                               windowsAbsolutePath, mask1);
-             if (result[ERROR_CODE] == ERROR_ACCESS_DENIED && mask2 != mask1)
-                 result = WindowsRegOpenKey1(rootNativeHandle(),
-                                             windowsAbsolutePath, mask2);
+            int[] result = WindowsRegOpenKey1(rootNativeHandle(),
+                                              windowsAbsolutePath, mask1);
+            if (result[ERROR_CODE] == ERROR_ACCESS_DENIED && mask2 != mask1)
+                result = WindowsRegOpenKey1(rootNativeHandle(),
+                                            windowsAbsolutePath, mask2);
 
-             if (result[ERROR_CODE] != ERROR_SUCCESS) {
-                logger().warning("Could not open windows "
-                + "registry node " + byteArrayToString(windowsAbsolutePath()) +
-                " at root 0x" + Integer.toHexString(rootNativeHandle()) +
-                ". Windows RegOpenKey(...) returned error code " +
-                result[ERROR_CODE] + ".");
+            if (result[ERROR_CODE] != ERROR_SUCCESS) {
+                logger().warning("Could not open windows registry node " +
+                        byteArrayToString(windowsAbsolutePath()) +
+                        " at root 0x" +
+                        Integer.toHexString(rootNativeHandle()) +
+                        ". Windows RegOpenKey(...) returned error code " +
+                        result[ERROR_CODE] + ".");
                 result[NATIVE_HANDLE] = NULL_NATIVE_HANDLE;
                 if (result[ERROR_CODE] == ERROR_ACCESS_DENIED) {
-                    throw new SecurityException("Could not open windows "
-                + "registry node " + byteArrayToString(windowsAbsolutePath()) +
-                " at root 0x" + Integer.toHexString(rootNativeHandle()) +
-                ": Access denied");
+                    throw new SecurityException(
+                            "Could not open windows registry node " +
+                            byteArrayToString(windowsAbsolutePath()) +
+                            " at root 0x" +
+                            Integer.toHexString(rootNativeHandle()) +
+                            ": Access denied");
                 }
-             }
-             return result[NATIVE_HANDLE];
+            }
+            return result[NATIVE_HANDLE];
         } else {
             return openKey(rootNativeHandle(), windowsAbsolutePath, mask1, mask2);
         }
@@ -548,21 +551,21 @@
                         int mask1, int mask2) {
     /* If the path is short enough open at once. Otherwise split the path */
         if (windowsRelativePath.length <= MAX_WINDOWS_PATH_LENGTH + 1 ) {
-             int[] result = WindowsRegOpenKey1(nativeHandle,
-                                               windowsRelativePath, mask1);
-             if (result[ERROR_CODE] == ERROR_ACCESS_DENIED && mask2 != mask1)
-                 result = WindowsRegOpenKey1(nativeHandle,
-                                             windowsRelativePath, mask2);
+            int[] result = WindowsRegOpenKey1(nativeHandle,
+                                              windowsRelativePath, mask1);
+            if (result[ERROR_CODE] == ERROR_ACCESS_DENIED && mask2 != mask1)
+                result = WindowsRegOpenKey1(nativeHandle,
+                                            windowsRelativePath, mask2);
 
-             if (result[ERROR_CODE] != ERROR_SUCCESS) {
-                logger().warning("Could not open windows "
-                + "registry node " + byteArrayToString(windowsAbsolutePath()) +
-                " at root 0x" + Integer.toHexString(nativeHandle) +
-                ". Windows RegOpenKey(...) returned error code " +
-                result[ERROR_CODE] + ".");
+            if (result[ERROR_CODE] != ERROR_SUCCESS) {
+                logger().warning("Could not open windows registry node " +
+                        byteArrayToString(windowsAbsolutePath()) +
+                        " at root 0x" + Integer.toHexString(nativeHandle) +
+                        ". Windows RegOpenKey(...) returned error code " +
+                        result[ERROR_CODE] + ".");
                 result[NATIVE_HANDLE] = NULL_NATIVE_HANDLE;
-             }
-             return result[NATIVE_HANDLE];
+            }
+            return result[NATIVE_HANDLE];
         } else {
             int separatorPosition = -1;
             // Be greedy - open the longest possible path
@@ -604,10 +607,12 @@
     private void closeKey(int nativeHandle) {
         int result = WindowsRegCloseKey(nativeHandle);
         if (result != ERROR_SUCCESS) {
-            logger().warning("Could not close windows "
-            + "registry node " + byteArrayToString(windowsAbsolutePath()) +
-            " at root 0x" + Integer.toHexString(rootNativeHandle()) +
-            ". Windows RegCloseKey(...) returned error code " + result + ".");
+            logger().warning("Could not close windows registry node " +
+                    byteArrayToString(windowsAbsolutePath()) +
+                    " at root 0x" +
+                    Integer.toHexString(rootNativeHandle()) +
+                    ". Windows RegCloseKey(...) returned error code " +
+                    result + ".");
         }
     }
 
@@ -627,10 +632,13 @@
                 toWindowsName(javaName), toWindowsValueString(value));
         if (result != ERROR_SUCCESS) {
             logger().warning("Could not assign value to key " +
-            byteArrayToString(toWindowsName(javaName))+ " at Windows registry node "
-           + byteArrayToString(windowsAbsolutePath()) + " at root 0x"
-           + Integer.toHexString(rootNativeHandle()) +
-           ". Windows RegSetValueEx(...) returned error code " + result + ".");
+                    byteArrayToString(toWindowsName(javaName)) +
+                    " at Windows registry node " +
+                    byteArrayToString(windowsAbsolutePath()) +
+                    " at root 0x" +
+                    Integer.toHexString(rootNativeHandle()) +
+                    ". Windows RegSetValueEx(...) returned error code " +
+                    result + ".");
             isBackingStoreAvailable = false;
         }
         closeKey(nativeHandle);
@@ -672,12 +680,12 @@
         int result =
             WindowsRegDeleteValue(nativeHandle, toWindowsName(key));
         if (result != ERROR_SUCCESS && result != ERROR_FILE_NOT_FOUND) {
-            logger().warning("Could not delete windows registry "
-            + "value " + byteArrayToString(windowsAbsolutePath())+ "\\" +
-            toWindowsName(key) + " at root 0x" +
-            Integer.toHexString(rootNativeHandle()) +
-            ". Windows RegDeleteValue(...) returned error code " +
-            result + ".");
+            logger().warning("Could not delete windows registry value " +
+                    byteArrayToString(windowsAbsolutePath()) + "\\" +
+                    toWindowsName(key) + " at root 0x" +
+                    Integer.toHexString(rootNativeHandle()) +
+                    ". Windows RegDeleteValue(...) returned error code " +
+                    result + ".");
             isBackingStoreAvailable = false;
         }
         closeKey(nativeHandle);
@@ -693,17 +701,20 @@
         // Find out the number of values
         int nativeHandle = openKey(KEY_QUERY_VALUE);
         if (nativeHandle == NULL_NATIVE_HANDLE) {
-            throw new BackingStoreException("Could not open windows"
-            + "registry node " + byteArrayToString(windowsAbsolutePath()) +
-            " at root 0x" + Integer.toHexString(rootNativeHandle()) + ".");
+            throw new BackingStoreException(
+                    "Could not open windows registry node " +
+                    byteArrayToString(windowsAbsolutePath()) +
+                    " at root 0x" +
+                    Integer.toHexString(rootNativeHandle()) + ".");
         }
         int[] result =  WindowsRegQueryInfoKey1(nativeHandle);
         if (result[ERROR_CODE] != ERROR_SUCCESS) {
-            String info = "Could not query windows"
-            + "registry node " + byteArrayToString(windowsAbsolutePath()) +
-            " at root 0x" + Integer.toHexString(rootNativeHandle()) +
-            ". Windows RegQueryInfoKeyEx(...) returned error code " +
-            result[ERROR_CODE] + ".";
+            String info = "Could not query windows registry node " +
+                    byteArrayToString(windowsAbsolutePath()) +
+                    " at root 0x" +
+                    Integer.toHexString(rootNativeHandle()) +
+                    ". Windows RegQueryInfoKeyEx(...) returned error code " +
+                    result[ERROR_CODE] + ".";
             logger().warning(info);
             throw new BackingStoreException(info);
         }
@@ -712,17 +723,17 @@
         if (valuesNumber == 0) {
             closeKey(nativeHandle);
             return new String[0];
-       }
-       // Get the values
-       String[] valueNames = new String[valuesNumber];
-       for (int i = 0; i < valuesNumber; i++) {
+        }
+        // Get the values
+        String[] valueNames = new String[valuesNumber];
+        for (int i = 0; i < valuesNumber; i++) {
             byte[] windowsName = WindowsRegEnumValue1(nativeHandle, i,
-                                                        maxValueNameLength+1);
+                                                      maxValueNameLength+1);
             if (windowsName == null) {
                 String info =
-                "Could not enumerate value #" + i + "  of windows node " +
-                byteArrayToString(windowsAbsolutePath()) + " at root 0x" +
-                Integer.toHexString(rootNativeHandle()) + ".";
+                    "Could not enumerate value #" + i + "  of windows node " +
+                    byteArrayToString(windowsAbsolutePath()) + " at root 0x" +
+                    Integer.toHexString(rootNativeHandle()) + ".";
                 logger().warning(info);
                 throw new BackingStoreException(info);
             }
@@ -740,20 +751,22 @@
      */
     protected String[] childrenNamesSpi() throws BackingStoreException {
         // Open key
-        int nativeHandle = openKey(KEY_ENUMERATE_SUB_KEYS| KEY_QUERY_VALUE);
+        int nativeHandle = openKey(KEY_ENUMERATE_SUB_KEYS | KEY_QUERY_VALUE);
         if (nativeHandle == NULL_NATIVE_HANDLE) {
-            throw new BackingStoreException("Could not open windows"
-            + "registry node " + byteArrayToString(windowsAbsolutePath()) +
-            " at root 0x" + Integer.toHexString(rootNativeHandle()) + ".");
+            throw new BackingStoreException(
+                    "Could not open windows registry node " +
+                    byteArrayToString(windowsAbsolutePath()) +
+                    " at root 0x" +
+                    Integer.toHexString(rootNativeHandle()) + ".");
         }
         // Get number of children
         int[] result =  WindowsRegQueryInfoKey1(nativeHandle);
         if (result[ERROR_CODE] != ERROR_SUCCESS) {
-            String info = "Could not query windows"
-            + "registry node " + byteArrayToString(windowsAbsolutePath()) +
-            " at root 0x" + Integer.toHexString(rootNativeHandle()) +
-            ". Windows RegQueryInfoKeyEx(...) returned error code " +
-            result[ERROR_CODE] + ".";
+            String info = "Could not query windows registry node " +
+                    byteArrayToString(windowsAbsolutePath()) +
+                    " at root 0x" + Integer.toHexString(rootNativeHandle()) +
+                    ". Windows RegQueryInfoKeyEx(...) returned error code " +
+                    result[ERROR_CODE] + ".";
             logger().warning(info);
             throw new BackingStoreException(info);
         }
@@ -768,12 +781,12 @@
         // Get children
         for (int i = 0; i < subKeysNumber; i++) {
             byte[] windowsName = WindowsRegEnumKeyEx1(nativeHandle, i,
-                                                                maxKeyLength+1);
+                                                      maxKeyLength+1);
             if (windowsName == null) {
                 String info =
-                "Could not enumerate key #" + i + "  of windows node " +
-                byteArrayToString(windowsAbsolutePath()) + " at root 0x" +
-                Integer.toHexString(rootNativeHandle()) + ". ";
+                    "Could not enumerate key #" + i + "  of windows node " +
+                    byteArrayToString(windowsAbsolutePath()) + " at root 0x" +
+                    Integer.toHexString(rootNativeHandle()) + ". ";
                 logger().warning(info);
                 throw new BackingStoreException(info);
             }
@@ -798,20 +811,24 @@
         }
         if (!isBackingStoreAvailable) {
             throw new BackingStoreException(
-                                       "flush(): Backing store not available.");
+                    "flush(): Backing store not available.");
         }
         int nativeHandle = openKey(KEY_READ);
         if (nativeHandle == NULL_NATIVE_HANDLE) {
-            throw new BackingStoreException("Could not open windows"
-            + "registry node " + byteArrayToString(windowsAbsolutePath()) +
-            " at root 0x" + Integer.toHexString(rootNativeHandle()) + ".");
+            throw new BackingStoreException(
+                    "Could not open windows registry node " +
+                    byteArrayToString(windowsAbsolutePath()) +
+                    " at root 0x" +
+                    Integer.toHexString(rootNativeHandle()) + ".");
         }
         int result = WindowsRegFlushKey1(nativeHandle);
         if (result != ERROR_SUCCESS) {
-            String info = "Could not flush windows "
-            + "registry node " + byteArrayToString(windowsAbsolutePath())
-            + " at root 0x" + Integer.toHexString(rootNativeHandle()) +
-            ". Windows RegFlushKey(...) returned error code " + result + ".";
+            String info = "Could not flush windows registry node " +
+                    byteArrayToString(windowsAbsolutePath()) +
+                    " at root 0x" +
+                    Integer.toHexString(rootNativeHandle()) +
+                    ". Windows RegFlushKey(...) returned error code " +
+                    result + ".";
             logger().warning(info);
             throw new BackingStoreException(info);
         }
@@ -838,7 +855,7 @@
      * Logs a warning message, if Windows Registry is unavailable.
      */
     protected AbstractPreferences childSpi(String name) {
-            return new WindowsPreferences(this, name);
+        return new WindowsPreferences(this, name);
     }
 
     /**
@@ -849,20 +866,22 @@
      */
     public void removeNodeSpi() throws BackingStoreException {
         int parentNativeHandle =
-                         ((WindowsPreferences)parent()).openKey(DELETE);
+                ((WindowsPreferences)parent()).openKey(DELETE);
         if (parentNativeHandle == NULL_NATIVE_HANDLE) {
-            throw new BackingStoreException("Could not open parent windows"
-            + "registry node of " + byteArrayToString(windowsAbsolutePath()) +
-            " at root 0x" + Integer.toHexString(rootNativeHandle()) + ".");
+            throw new BackingStoreException(
+                    "Could not open parent windows registry node of " +
+                    byteArrayToString(windowsAbsolutePath()) +
+                    " at root 0x" +
+                    Integer.toHexString(rootNativeHandle()) + ".");
         }
         int result =
                 WindowsRegDeleteKey(parentNativeHandle, toWindowsName(name()));
         if (result != ERROR_SUCCESS) {
-            String info = "Could not delete windows "
-            + "registry node " + byteArrayToString(windowsAbsolutePath()) +
-            " at root 0x" + Integer.toHexString(rootNativeHandle()) +
-            ". Windows RegDeleteKeyEx(...) returned error code " +
-            result + ".";
+            String info = "Could not delete windows registry node " +
+                    byteArrayToString(windowsAbsolutePath()) +
+                    " at root 0x" + Integer.toHexString(rootNativeHandle()) +
+                    ". Windows RegDeleteKeyEx(...) returned error code " +
+                    result + ".";
             logger().warning(info);
             throw new BackingStoreException(info);
         }
@@ -879,23 +898,25 @@
     private static String toJavaName(byte[] windowsNameArray) {
         String windowsName = byteArrayToString(windowsNameArray);
         // check if Alt64
-        if ((windowsName.length()>1) &&
-                                   (windowsName.substring(0,2).equals("/!"))) {
+        if ((windowsName.length() > 1) &&
+                (windowsName.substring(0, 2).equals("/!"))) {
             return toJavaAlt64Name(windowsName);
         }
-        StringBuffer javaName = new StringBuffer();
+        StringBuilder javaName = new StringBuilder();
         char ch;
         // Decode from simple encoding
-        for (int i = 0; i < windowsName.length(); i++){
+        for (int i = 0; i < windowsName.length(); i++) {
             if ((ch = windowsName.charAt(i)) == '/') {
                 char next = ' ';
                 if ((windowsName.length() > i + 1) &&
-                   ((next = windowsName.charAt(i+1)) >= 'A') && (next <= 'Z')) {
-                ch = next;
-                i++;
-                } else  if ((windowsName.length() > i + 1) && (next == '/')) {
-                ch = '\\';
-                i++;
+                        ((next = windowsName.charAt(i+1)) >= 'A') &&
+                        (next <= 'Z')) {
+                    ch = next;
+                    i++;
+                } else if ((windowsName.length() > i + 1) &&
+                           (next == '/')) {
+                    ch = '\\';
+                    i++;
                 }
             } else if (ch == '\\') {
                 ch = '/';
@@ -914,8 +935,8 @@
 
     private static String toJavaAlt64Name(String windowsName) {
         byte[] byteBuffer =
-                          Base64.altBase64ToByteArray(windowsName.substring(2));
-        StringBuffer result = new StringBuffer();
+                Base64.altBase64ToByteArray(windowsName.substring(2));
+        StringBuilder result = new StringBuilder();
         for (int i = 0; i < byteBuffer.length; i++) {
             int firstbyte = (byteBuffer[i++] & 0xff);
             int secondbyte =  (byteBuffer[i] & 0xff);
@@ -945,10 +966,10 @@
      * Base64 class.
      */
     private static byte[] toWindowsName(String javaName) {
-        StringBuffer windowsName = new StringBuffer();
+        StringBuilder windowsName = new StringBuilder();
         for (int i = 0; i < javaName.length(); i++) {
-            char ch =javaName.charAt(i);
-            if ((ch < 0x0020)||(ch > 0x007f)) {
+            char ch = javaName.charAt(i);
+            if ((ch < 0x0020) || (ch > 0x007f)) {
                 // If a non-trivial character encountered, use altBase64
                 return toWindowsAlt64Name(javaName);
             }
@@ -957,7 +978,7 @@
             } else if (ch == '/') {
                 windowsName.append('\\');
             } else if ((ch >= 'A') && (ch <='Z')) {
-                windowsName.append("/" + ch);
+                windowsName.append('/').append(ch);
             } else {
                 windowsName.append(ch);
             }
@@ -976,13 +997,13 @@
         // Convert to byte pairs
         int counter = 0;
         for (int i = 0; i < javaName.length();i++) {
-                int ch = javaName.charAt(i);
-                javaNameArray[counter++] = (byte)(ch >>> 8);
-                javaNameArray[counter++] = (byte)ch;
+            int ch = javaName.charAt(i);
+            javaNameArray[counter++] = (byte)(ch >>> 8);
+            javaNameArray[counter++] = (byte)ch;
         }
 
-        return stringToByteArray(
-                           "/!" + Base64.byteArrayToAltBase64(javaNameArray));
+        return stringToByteArray("/!" +
+                Base64.byteArrayToAltBase64(javaNameArray));
     }
 
     /**
@@ -994,30 +1015,31 @@
      private static String toJavaValueString(byte[] windowsNameArray) {
         // Use modified native2ascii algorithm
         String windowsName = byteArrayToString(windowsNameArray);
-        StringBuffer javaName = new StringBuffer();
+        StringBuilder javaName = new StringBuilder();
         char ch;
         for (int i = 0; i < windowsName.length(); i++){
             if ((ch = windowsName.charAt(i)) == '/') {
                 char next = ' ';
 
                 if (windowsName.length() > i + 1 &&
-                                    (next = windowsName.charAt(i + 1)) == 'u') {
-                    if (windowsName.length() < i + 6){
+                        (next = windowsName.charAt(i + 1)) == 'u') {
+                    if (windowsName.length() < i + 6) {
                         break;
                     } else {
-                        ch = (char)Integer.parseInt
-                                      (windowsName.substring(i + 2, i + 6), 16);
+                        ch = (char)Integer.parseInt(
+                                windowsName.substring(i + 2, i + 6), 16);
                         i += 5;
                     }
                 } else
                 if ((windowsName.length() > i + 1) &&
-                          ((windowsName.charAt(i+1)) >= 'A') && (next <= 'Z')) {
-                ch = next;
-                i++;
-                } else  if ((windowsName.length() > i + 1) &&
-                                               (next == '/')) {
-                ch = '\\';
-                i++;
+                        ((windowsName.charAt(i+1)) >= 'A') &&
+                        (next <= 'Z')) {
+                    ch = next;
+                    i++;
+                } else if ((windowsName.length() > i + 1) &&
+                        (next == '/')) {
+                    ch = '\\';
+                    i++;
                 }
             } else if (ch == '\\') {
                 ch = '/';
@@ -1037,14 +1059,14 @@
      * to convert java string to a byte array of ASCII characters.
      */
     private static byte[] toWindowsValueString(String javaName) {
-        StringBuffer windowsName = new StringBuffer();
+        StringBuilder windowsName = new StringBuilder();
         for (int i = 0; i < javaName.length(); i++) {
-            char ch =javaName.charAt(i);
-            if ((ch < 0x0020)||(ch > 0x007f)){
+            char ch = javaName.charAt(i);
+            if ((ch < 0x0020) || (ch > 0x007f)){
                 // write \udddd
                 windowsName.append("/u");
                 String hex = Integer.toHexString(javaName.charAt(i));
-                StringBuffer hex4 = new StringBuffer(hex);
+                StringBuilder hex4 = new StringBuilder(hex);
                 hex4.reverse();
                 int len = 4 - hex4.length();
                 for (int j = 0; j < len; j++){
@@ -1058,7 +1080,7 @@
             } else if (ch == '/') {
                 windowsName.append('\\');
             } else if ((ch >= 'A') && (ch <='Z')) {
-                windowsName.append("/" + ch);
+                windowsName.append('/').append(ch);
             } else {
                 windowsName.append(ch);
             }
@@ -1070,8 +1092,9 @@
      * Returns native handle for the top Windows node for this node.
      */
     private int rootNativeHandle() {
-        return (isUserNode()? USER_ROOT_NATIVE_HANDLE :
-                              SYSTEM_ROOT_NATIVE_HANDLE);
+        return (isUserNode()
+                ? USER_ROOT_NATIVE_HANDLE
+                : SYSTEM_ROOT_NATIVE_HANDLE);
     }
 
     /**
@@ -1090,7 +1113,7 @@
      * Converts a null-terminated byte array to java string
      */
     private static String byteArrayToString(byte[] array) {
-        StringBuffer result = new StringBuffer();
+        StringBuilder result = new StringBuilder();
         for (int i = 0; i < array.length - 1; i++) {
             result.append((char)array[i]);
         }
--- a/jdk/src/java.rmi/share/classes/com/sun/rmi/rmid/ExecOptionPermission.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.rmi/share/classes/com/sun/rmi/rmid/ExecOptionPermission.java	Wed Jul 05 20:35:10 2017 +0200
@@ -32,7 +32,6 @@
 /**
  * The ExecOptionPermission class represents permission for rmid to use
  * a specific command-line option when launching an activation group.
- * <P>
  *
  * @author Ann Wollrath
  *
@@ -68,9 +67,9 @@
      * Checks if the specified permission is "implied" by
      * this object.
      * <P>
-     * More specifically, this method returns true if:<p>
+     * More specifically, this method returns true if:
      * <ul>
-     * <li> <i>p</i>'s class is the same as this object's class, and<p>
+     * <li> <i>p</i>'s class is the same as this object's class, and
      * <li> <i>p</i>'s name equals or (in the case of wildcards)
      *      is implied by this object's
      *      name. For example, "a.b.*" implies "a.b.c", and
@@ -111,7 +110,7 @@
      * Checks two ExecOptionPermission objects for equality.
      * Checks that <i>obj</i>'s class is the same as this object's class
      * and has the same name as this object.
-     * <P>
+     *
      * @param obj the object we are testing for equality with this object.
      * @return true if <i>obj</i> is an ExecOptionPermission, and has the same
      * name as this ExecOptionPermission object, false otherwise.
@@ -154,7 +153,7 @@
      * Returns a new PermissionCollection object for storing
      * ExecOptionPermission objects.
      * <p>
-     * A ExecOptionPermissionCollection stores a collection of
+     * An ExecOptionPermissionCollection stores a collection of
      * ExecOptionPermission permissions.
      *
      * <p>ExecOptionPermission objects must be stored in a manner that allows
--- a/jdk/src/java.rmi/share/classes/com/sun/rmi/rmid/ExecPermission.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.rmi/share/classes/com/sun/rmi/rmid/ExecPermission.java	Wed Jul 05 20:35:10 2017 +0200
@@ -40,14 +40,13 @@
  * all the files and directories contained in that directory. A pathname
  * that ends with "/-" indicates (recursively) all files
  * and subdirectories contained in that directory. A pathname consisting of
- * the special token "&lt;&lt;ALL FILES&gt;&gt;" matches <bold>any</bold> file.
+ * the special token "{@code <<ALL FILES>>}" matches <b>any</b> file.
  * <P>
  * Note: A pathname consisting of a single "*" indicates all the files
  * in the current directory, while a pathname consisting of a single "-"
  * indicates all the files in the current directory and
  * (recursively) all files and subdirectories contained in the current
  * directory.
- * <P>
  *
  *
  * @author Ann Wollrath
@@ -72,7 +71,7 @@
      * a directory and all the files contained in that directory. A pathname
      * that ends with "/-" indicates a directory and (recursively) all files
      * and subdirectories contained in that directory. The special pathname
-     * "&lt;&lt;ALL FILES&gt;&gt;" matches all files.
+     * "{@code <<ALL FILES>>}" matches all files.
      *
      * <p>A pathname consisting of a single "*" indicates all the files
      * in the current directory, while a pathname consisting of a single "-"
@@ -96,7 +95,7 @@
      * a directory and all the files contained in that directory. A pathname
      * that ends with "/-" indicates a directory and (recursively) all files
      * and subdirectories contained in that directory. The special pathname
-     * "&lt;&lt;ALL FILES&gt;&gt;" matches all files.
+     * "{@code <<ALL FILES>>}" matches all files.
      *
      * <p>A pathname consisting of a single "*" indicates all the files
      * in the current directory, while a pathname consisting of a single "-"
@@ -114,9 +113,9 @@
     /**
      * Checks if this ExecPermission object "implies" the specified permission.
      * <P>
-     * More specifically, this method returns true if:<p>
+     * More specifically, this method returns true if:
      * <ul>
-     * <li> <i>p</i> is an instanceof ExecPermission,<p> and
+     * <li> <i>p</i> is an instanceof ExecPermission, and
      * <li> <i>p</i>'s pathname is implied by this object's
      *      pathname. For example, "/tmp/*" implies "/tmp/foo", since
      *      "/tmp/*" encompasses the "/tmp" directory and all files in that
@@ -140,7 +139,7 @@
      * Checks two ExecPermission objects for equality.
      * Checks that <i>obj</i>'s class is the same as this object's class
      * and has the same name as this object.
-     * <P>
+     *
      * @param obj the object we are testing for equality with this object.
      * @return true if <i>obj</i> is an ExecPermission, and has the same
      * pathname as this ExecPermission object, false otherwise.
--- a/jdk/src/java.rmi/share/classes/sun/rmi/log/LogInputStream.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.rmi/share/classes/sun/rmi/log/LogInputStream.java	Wed Jul 05 20:35:10 2017 +0200
@@ -35,7 +35,7 @@
     /**
      * Creates a log input file with the specified system dependent
      * file descriptor.
-     * @param fd the system dependent file descriptor
+     * @param in the system dependent file descriptor
      * @param length the total number of bytes allowed to be read
      * @exception IOException If an I/O error has occurred.
      */
--- a/jdk/src/java.rmi/share/classes/sun/rmi/log/LogOutputStream.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.rmi/share/classes/sun/rmi/log/LogOutputStream.java	Wed Jul 05 20:35:10 2017 +0200
@@ -35,7 +35,7 @@
     /**
      * Creates an output file with the specified system dependent
      * file descriptor.
-     * @param fd the system dependent file descriptor
+     * @param raf the system dependent file descriptor.
      * @exception IOException If an I/O error has occurred.
      */
     public LogOutputStream(RandomAccessFile raf) throws IOException {
--- a/jdk/src/java.rmi/share/classes/sun/rmi/log/ReliableLog.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.rmi/share/classes/sun/rmi/log/ReliableLog.java	Wed Jul 05 20:35:10 2017 +0200
@@ -124,7 +124,7 @@
      * stable storage directory.
      *
      * @param dirPath path to the stable storage directory
-     * @param logCl the closure object containing callbacks for logging and
+     * @param handler the closure object containing callbacks for logging and
      * recovery
      * @param pad ignored
      * @exception IOException If a directory creation error has
@@ -170,8 +170,8 @@
      * stable storage directory.
      *
      * @param dirPath path to the stable storage directory
-     * @param logCl the closure object containing callbacks for logging and
-     * recovery
+     * @param handler the closure object containing callbacks for logging and
+     *        recovery
      * @exception IOException If a directory creation error has
      * occurred or if initialSnapshot callback raises an exception
      */
--- a/jdk/src/java.rmi/share/classes/sun/rmi/registry/RegistryImpl.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.rmi/share/classes/sun/rmi/registry/RegistryImpl.java	Wed Jul 05 20:35:10 2017 +0200
@@ -155,7 +155,7 @@
     /**
      * Returns the remote object for specified name in the registry.
      * @exception RemoteException If remote operation failed.
-     * @exception NotBound If name is not currently bound.
+     * @exception NotBoundException If name is not currently bound.
      */
     public Remote lookup(String name)
         throws RemoteException, NotBoundException
@@ -188,7 +188,7 @@
     /**
      * Unbind the name.
      * @exception RemoteException If remote operation failed.
-     * @exception NotBound If name is not currently bound.
+     * @exception NotBoundException If name is not currently bound.
      */
     public void unbind(String name)
         throws RemoteException, NotBoundException, AccessException
--- a/jdk/src/java.rmi/share/classes/sun/rmi/runtime/Log.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.rmi/share/classes/sun/rmi/runtime/Log.java	Wed Jul 05 20:35:10 2017 +0200
@@ -96,7 +96,7 @@
      * care to interpret a range of values between BRIEF, VERBOSE and
      * SILENT.
      *
-     * An override < 0 is interpreted to mean that the logging
+     * An override {@literal <} 0 is interpreted to mean that the logging
      * configuration should not be overridden. The level passed to the
      * factories createLog method will be null in this case.
      *
--- a/jdk/src/java.rmi/share/classes/sun/rmi/server/ActivationGroupImpl.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.rmi/share/classes/sun/rmi/server/ActivationGroupImpl.java	Wed Jul 05 20:35:10 2017 +0200
@@ -345,7 +345,7 @@
     * request.
     *
     * @param id the object's activation identifier
-    * @returns true if the operation succeeds (the operation will
+    * @return true if the operation succeeds (the operation will
     * succeed if the object in currently known to be active and is
     * either already unexported or is currently exported and has no
     * pending/executing calls); false is returned if the object has
@@ -430,7 +430,7 @@
      * hasn't already done so.
      *
      * @param id the object's identifier
-     * @param obj the remote object implementation
+     * @param impl the remote object implementation
      * @exception UnknownObjectException if object is not registered
      * @exception RemoteException if call informing monitor fails
      */
--- a/jdk/src/java.rmi/share/classes/sun/rmi/server/ActivationGroupInit.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.rmi/share/classes/sun/rmi/server/ActivationGroupInit.java	Wed Jul 05 20:35:10 2017 +0200
@@ -36,7 +36,7 @@
  * The activator spawns (as a child process) an activation group as needed
  * and directs activation requests to the appropriate activation
  * group. After spawning the VM, the activator passes some
- * information to the bootstrap code via its stdin: <p>
+ * information to the bootstrap code via its stdin:
  * <ul>
  * <li> the activation group's id,
  * <li> the activation group's descriptor (an instance of the class
--- a/jdk/src/java.rmi/share/classes/sun/rmi/transport/Channel.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.rmi/share/classes/sun/rmi/transport/Channel.java	Wed Jul 05 20:35:10 2017 +0200
@@ -42,7 +42,7 @@
 
     /**
      * Free the connection generated by this channel.
-     * @param c The connection
+     * @param conn The connection.
      * @param reuse If true, the connection is in a state in which it
      *        can be reused for another method call.
      */
--- a/jdk/src/java.rmi/share/classes/sun/rmi/transport/LiveRef.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.rmi/share/classes/sun/rmi/transport/LiveRef.java	Wed Jul 05 20:35:10 2017 +0200
@@ -56,7 +56,7 @@
 
     /**
      * Construct a "well-known" live reference to a remote object
-     * @param isLocalServer If true, indicates this ref specifies a local
+     * @param isLocal If true, indicates this ref specifies a local
      * server in this address space; if false, the ref is for a remote
      * object (hence a surrogate or proxy) in another address space.
      */
--- a/jdk/src/java.rmi/share/classes/sun/rmi/transport/proxy/CGIHandler.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.rmi/share/classes/sun/rmi/transport/proxy/CGIHandler.java	Wed Jul 05 20:35:10 2017 +0200
@@ -81,7 +81,7 @@
 /**
  * The CGIHandler class contains methods for executing as a CGI program.
  * The main function interprets the query string as a command of the form
- * "<command>=<parameters>".
+ * "{@code <command>=<parameters>}".
  *
  * This class depends on the CGI 1.0 environment variables being set as
  * properties of the same name in this Java VM.
--- a/jdk/src/java.scripting/share/classes/javax/script/Compilable.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.scripting/share/classes/javax/script/Compilable.java	Wed Jul 05 20:35:10 2017 +0200
@@ -42,7 +42,7 @@
      *
      * @param script The source of the script, represented as a <code>String</code>.
      *
-     * @return An subclass of <code>CompiledScript</code> to be executed later using one
+     * @return An instance of a subclass of <code>CompiledScript</code> to be executed later using one
      * of the <code>eval</code> methods of <code>CompiledScript</code>.
      *
      * @throws ScriptException if compilation fails.
@@ -61,7 +61,7 @@
      *
      * @param script The reader from which the script source is obtained.
      *
-     * @return An implementation of <code>CompiledScript</code> to be executed
+     * @return An instance of a subclass of <code>CompiledScript</code> to be executed
      * later using one of its <code>eval</code> methods of <code>CompiledScript</code>.
      *
      * @throws ScriptException if compilation fails.
--- a/jdk/src/java.scripting/share/classes/javax/script/SimpleScriptContext.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.scripting/share/classes/javax/script/SimpleScriptContext.java	Wed Jul 05 20:35:10 2017 +0200
@@ -140,6 +140,7 @@
      * @throws IllegalArgumentException if the name is empty.
      */
     public Object getAttribute(String name) {
+        checkName(name);
         if (engineScope.containsKey(name)) {
             return getAttribute(name, ENGINE_SCOPE);
         } else if (globalScope != null && globalScope.containsKey(name)) {
@@ -162,7 +163,7 @@
      * @throws NullPointerException if the name is null.
      */
     public Object getAttribute(String name, int scope) {
-
+        checkName(name);
         switch (scope) {
 
             case ENGINE_SCOPE:
@@ -191,7 +192,7 @@
      * @throws NullPointerException if the name is null.
      */
     public Object removeAttribute(String name, int scope) {
-
+        checkName(name);
         switch (scope) {
 
             case ENGINE_SCOPE:
@@ -223,7 +224,7 @@
      * @throws NullPointerException if the name is null.
      */
     public void setAttribute(String name, Object value, int scope) {
-
+        checkName(name);
         switch (scope) {
 
             case ENGINE_SCOPE:
@@ -281,6 +282,7 @@
      * @throws IllegalArgumentException if name is empty.
      */
     public int getAttributesScope(String name) {
+        checkName(name);
         if (engineScope.containsKey(name)) {
             return ENGINE_SCOPE;
         } else if (globalScope != null && globalScope.containsKey(name)) {
@@ -314,6 +316,13 @@
         return scopes;
     }
 
+    private void checkName(String name) {
+        Objects.requireNonNull(name);
+        if (name.isEmpty()) {
+            throw new IllegalArgumentException("name cannot be empty");
+        }
+    }
+
     private static List<Integer> scopes;
     static {
         scopes = new ArrayList<Integer>(2);
--- a/jdk/src/java.scripting/share/classes/javax/script/package.html	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.scripting/share/classes/javax/script/package.html	Wed Jul 05 20:35:10 2017 +0200
@@ -29,7 +29,7 @@
 </head>
 <body bgcolor="white">
 <p>The scripting API consists of interfaces and classes that define
-Java <font size=1><sup>TM</sup></font> Scripting Engines and provides
+Java&trade; Scripting Engines and provides
 a framework for their use in Java applications. This API is intended
 for use by application programmers who wish to execute programs
 written in scripting languages in their Java applications. The
--- a/jdk/src/java.security.jgss/share/classes/sun/security/krb5/Config.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.security.jgss/share/classes/sun/security/krb5/Config.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1085,27 +1085,30 @@
      * Check if need to use DNS to locate Kerberos services for name. If not
      * defined, check dns_fallback, whose default value is true.
      */
-    private boolean useDNS(String name) {
+    private boolean useDNS(String name, boolean defaultValue) {
         Boolean value = getBooleanObject("libdefaults", name);
         if (value != null) {
             return value.booleanValue();
-        } else {
-            return getBooleanObject("libdefaults", "dns_fallback") != Boolean.FALSE;
         }
+        value = getBooleanObject("libdefaults", "dns_fallback");
+        if (value != null) {
+            return value.booleanValue();
+        }
+        return defaultValue;
     }
 
     /**
      * Check if need to use DNS to locate the KDC
      */
     private boolean useDNS_KDC() {
-        return useDNS("dns_lookup_kdc");
+        return useDNS("dns_lookup_kdc", true);
     }
 
     /*
      * Check if need to use DNS to locate the Realm
      */
     private boolean useDNS_Realm() {
-        return useDNS("dns_lookup_realm");
+        return useDNS("dns_lookup_realm", false);
     }
 
     /**
--- a/jdk/src/java.sql.rowset/share/classes/com/sun/rowset/FilteredRowSetImpl.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.sql.rowset/share/classes/com/sun/rowset/FilteredRowSetImpl.java	Wed Jul 05 20:35:10 2017 +0200
@@ -466,7 +466,7 @@
      *                        passed to the evaluate function.
      * 2. updateXXXstream() - here it would suffice to pass the stream handle
      *                        to the evaluate function and the implementation
-     *                        of the evaluate function can do the comparision
+     *                        of the evaluate function can do the comparison
      *                        based on the stream and also type of data.
      */
 
--- a/jdk/src/java.sql.rowset/share/classes/com/sun/rowset/JoinRowSetImpl.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.sql.rowset/share/classes/com/sun/rowset/JoinRowSetImpl.java	Wed Jul 05 20:35:10 2017 +0200
@@ -4063,14 +4063,16 @@
     }
 
     /**
-     * Provide interface coverage for getURL(int) in ResultSet->RowSet
+     * Provide interface coverage for getURL(int) in
+     * ResultSet{@literal ->}RowSet
      */
     public java.net.URL getURL(int columnIndex) throws SQLException {
         return crsInternal.getURL(columnIndex);
     }
 
     /**
-     * Provide interface coverage for getURL(String) in ResultSet->RowSet
+     * Provide interface coverage for getURL(String) in
+     * ResultSet{@literal ->}RowSet
      */
     public java.net.URL getURL(String columnName) throws SQLException {
         return crsInternal.getURL(columnName);
--- a/jdk/src/java.sql.rowset/share/classes/com/sun/rowset/providers/RIOptimisticProvider.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.sql.rowset/share/classes/com/sun/rowset/providers/RIOptimisticProvider.java	Wed Jul 05 20:35:10 2017 +0200
@@ -36,7 +36,7 @@
  * The reference implementation of a JDBC Rowset synchronization provider
  * providing optimistic synchronization with a relational datastore
  * using any JDBC technology-enabled driver.
- * <p>
+ *
  * <h3>1.0 Backgroud</h3>
  * This synchronization provider is registered with the
  * <code>SyncFactory</code> by default as the
--- a/jdk/src/java.sql.rowset/share/classes/javax/sql/rowset/serial/SerialBlob.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.sql.rowset/share/classes/javax/sql/rowset/serial/SerialBlob.java	Wed Jul 05 20:35:10 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
@@ -67,7 +67,7 @@
      * value of this <code>SerialBlob</code> object.
      * @serial
      */
-    private byte buf[];
+    private byte[] buf;
 
     /**
      * The internal representation of the <code>Blob</code> object on which this
@@ -103,12 +103,13 @@
      * @throws SerialException if an error occurs during serialization
      * @throws SQLException if a SQL errors occurs
      */
-    public SerialBlob(byte[] b) throws SerialException, SQLException {
+    public SerialBlob(byte[] b)
+            throws SerialException, SQLException {
 
         len = b.length;
         buf = new byte[(int)len];
         for(int i = 0; i < len; i++) {
-           buf[i] = b[i];
+            buf[i] = b[i];
         }
         origLen = len;
     }
@@ -133,19 +134,17 @@
      *     to this constructor is a <code>null</code>.
      * @see java.sql.Blob
      */
-    public SerialBlob (Blob blob) throws SerialException, SQLException {
+    public SerialBlob (Blob blob)
+            throws SerialException, SQLException {
 
         if (blob == null) {
-            throw new SQLException("Cannot instantiate a SerialBlob " +
-                 "object with a null Blob object");
+            throw new SQLException(
+                    "Cannot instantiate a SerialBlob object with a null Blob object");
         }
 
         len = blob.length();
         buf = blob.getBytes(1, (int)len );
         this.blob = blob;
-
-         //if ( len < 10240000)
-         // len = 10240000;
         origLen = len;
     }
 
@@ -246,7 +245,8 @@
      *         value from the database
      */
     public long position(byte[] pattern, long start)
-                throws SerialException, SQLException {
+            throws SerialException, SQLException {
+
         isValid();
         if (start < 1 || start > len) {
             return -1;
@@ -291,7 +291,7 @@
      *         value from the database
      */
     public long position(Blob pattern, long start)
-       throws SerialException, SQLException {
+            throws SerialException, SQLException {
         isValid();
         return position(pattern.getBytes(1, (int)(pattern.length())), start);
     }
@@ -317,8 +317,8 @@
      * @see #getBytes
      */
     public int setBytes(long pos, byte[] bytes)
-        throws SerialException, SQLException {
-        return (setBytes(pos, bytes, 0, bytes.length));
+            throws SerialException, SQLException {
+        return setBytes(pos, bytes, 0, bytes.length);
     }
 
     /**
@@ -353,7 +353,7 @@
      * @see #getBytes
      */
     public int setBytes(long pos, byte[] bytes, int offset, int length)
-        throws SerialException, SQLException {
+            throws SerialException, SQLException {
 
         isValid();
         if (offset < 0 || offset > bytes.length) {
@@ -370,7 +370,7 @@
 
         if ((length + offset) > bytes.length) {
             throw new SerialException("Invalid OffSet. Cannot have combined offset " +
-                "and length that is greater that the Blob buffer");
+                    "and length that is greater that the Blob buffer");
         }
 
         int i = 0;
@@ -403,7 +403,8 @@
      * @see #getBinaryStream
      */
     public java.io.OutputStream setBinaryStream(long pos)
-        throws SerialException, SQLException {
+            throws SerialException, SQLException {
+
         isValid();
         if (this.blob != null) {
             return this.blob.setBinaryStream(pos);
@@ -426,17 +427,16 @@
      * if {@code free} had previously been called on this object
      */
     public void truncate(long length) throws SerialException {
-
         isValid();
         if (length > len) {
-           throw new SerialException
-              ("Length more than what can be truncated");
+            throw new SerialException(
+                    "Length more than what can be truncated");
         } else if((int)length == 0) {
-             buf = new byte[0];
-             len = length;
+            buf = new byte[0];
+            len = length;
         } else {
-             len = length;
-             buf = this.getBytes(1, (int)len);
+            len = length;
+            buf = this.getBytes(1, (int)len);
         }
     }
 
@@ -467,8 +467,8 @@
             throw new SerialException("Invalid position in BLOB object set");
         }
         if (length < 1 || length > len - pos + 1) {
-            throw new SerialException("length is < 1 or pos + length >"
-                    + "total number of bytes");
+            throw new SerialException(
+                    "length is < 1 or pos + length > total number of bytes");
         }
         return new ByteArrayInputStream(buf, (int) pos - 1, (int) length);
     }
@@ -537,14 +537,13 @@
     public Object clone() {
         try {
             SerialBlob sb = (SerialBlob) super.clone();
-            sb.buf =  (buf != null) ? Arrays.copyOf(buf, (int)len) : null;
+            sb.buf = (buf != null) ? Arrays.copyOf(buf, (int)len) : null;
             sb.blob = null;
             return sb;
         } catch (CloneNotSupportedException ex) {
             // this shouldn't happen, since we are Cloneable
             throw new InternalError();
         }
-
     }
 
     /**
@@ -555,15 +554,15 @@
             throws IOException, ClassNotFoundException {
 
         ObjectInputStream.GetField fields = s.readFields();
-       byte[] tmp = (byte[])fields.get("buf", null);
-       if (tmp == null)
-           throw new InvalidObjectException("buf is null and should not be!");
-       buf = tmp.clone();
-       len = fields.get("len", 0L);
-       if (buf.length != len)
-           throw new InvalidObjectException("buf is not the expected size");
-       origLen = fields.get("origLen", 0L);
-       blob = (Blob) fields.get("blob", null);
+        byte[] tmp = (byte[])fields.get("buf", null);
+        if (tmp == null)
+            throw new InvalidObjectException("buf is null and should not be!");
+        buf = tmp.clone();
+        len = fields.get("len", 0L);
+        if (buf.length != len)
+            throw new InvalidObjectException("buf is not the expected size");
+        origLen = fields.get("origLen", 0L);
+        blob = (Blob) fields.get("blob", null);
     }
 
     /**
@@ -591,8 +590,8 @@
      */
     private void isValid() throws SerialException {
         if (buf == null) {
-            throw new SerialException("Error: You cannot call a method on a "
-                    + "SerialBlob instance once free() has been called.");
+            throw new SerialException("Error: You cannot call a method on a " +
+                    "SerialBlob instance once free() has been called.");
         }
     }
 
--- a/jdk/src/java.sql/share/classes/java/sql/package.html	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.sql/share/classes/java/sql/package.html	Wed Jul 05 20:35:10 2017 +0200
@@ -34,10 +34,10 @@
 
 Provides the API for accessing and processing data stored in a 
 data source (usually a relational database) using the 
-Java<sup><font size=-2>TM</font></sup> programming language. 
+Java&trade; programming language. 
 This API includes a framework whereby different
 drivers can be installed dynamically to access different data sources.
-Although the JDBC<sup><font size=-2>TM</font></sup> API is mainly geared 
+Although the JDBC&trade; API is mainly geared 
 to passing SQL statements to a database, it provides for reading and
 writing data from any data source with a tabular format.
 The reader/writer facility, available through the 
@@ -45,17 +45,16 @@
 use and update data from a spread sheet, flat file, or any other tabular 
 data source.
 
-<h2>What the JDBC<sup><font size=-2>TM</font></sup> 4.2 API Includes</h2>
-The JDBC<sup><font size=-2>TM</font></sup> 4.2 API includes both
+<h2>What the JDBC&trade; 4.2 API Includes</h2>
+The JDBC&trade; 4.2 API includes both
 the <code>java.sql</code> package, referred to as the JDBC core API,
 and the <code>javax.sql</code> package, referred to as the JDBC Optional
 Package API. This complete JDBC API
-is included in the Java<sup><font size=-2>TM</font></sup>  
-Standard Edition (Java SE<sup><font size=-2>TM</font></sup>), version 7.
+is included in the Java&trade; Standard Edition (Java SE&trade;), version 7.
 The <code>javax.sql</code> package extends the functionality of the JDBC API 
 from a client-side API to a server-side API, and it is an essential part
-of the Java<sup><font size=-2>TM</font></sup>  Enterprise Edition
-(Java EE<sup><font size=-2>TM</font></sup>) technology. 
+of the Java&trade;  Enterprise Edition
+(Java EE&trade;) technology. 
 
 <h2>Versions</h2>
 The JDBC 4.2 API incorporates all of the previous JDBC API versions:
@@ -74,7 +73,7 @@
 Classes, interfaces, methods, fields, constructors, and exceptions 
 have the following "since" tags that indicate when they were introduced 
 into the Java platform. When these "since" tags are used in
-Javadoc<sup><font size=-2>TM</font></sup> comments for the JDBC API,
+Javadoc&trade; comments for the JDBC API,
 they indicate the following:
 <UL>
     <LI>Since 1.8 -- new in the JDBC 4.2 API and part of the Java SE platform,
@@ -88,7 +87,7 @@
  <LI>Since 1.2 -- new in the JDBC 2.0 API and part of the J2SE platform, 
      version 1.2</li>
  <LI>Since 1.1 or no "since" tag -- in the original JDBC 1.0 API and part of
-     the JDK<sup><font size=-2>TM</font></sup>, version 1.1</li>
+     the JDK&trade;, version 1.1</li>
 </UL>
 <P>
 <b>NOTE:</b> Many of the new features are optional; consequently, there is 
@@ -97,7 +96,7 @@
 you try to use it.
 <P>
 <b>NOTE:</b> The class <code>SQLPermission</code> was added in the
-Java<sup><font size=-2>TM</font></sup> 2 SDK, Standard Edition, 
+Java&trade; 2 SDK, Standard Edition, 
 version 1.3 release. This class is used to prevent unauthorized
 access to the logging stream associated with the <code>DriverManager</code>,
 which may contain information such as table names, column data, and so on.
@@ -277,7 +276,7 @@
 Package API</h3>
 <UL>
   <LI>The <code>DataSource</code> interface as a means of making a connection.  The
-      Java Naming and Directory Interface<sup><font size=-2>TM</font></sup>
+      Java Naming and Directory Interface&trade;
       (JNDI) is used for registering a <code>DataSource</code> object with a 
       naming service and also for  retrieving it.
   <LI>Pooled connections -- allowing connections to be used and reused
--- a/jdk/src/java.sql/share/classes/javax/sql/package.html	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.sql/share/classes/javax/sql/package.html	Wed Jul 05 20:35:10 2017 +0200
@@ -33,7 +33,7 @@
 <body bgcolor="white">
 
 Provides the API for server side data source access and processing from
-the Java<sup><font size=-2>TM</font></sup> programming language.
+the Java&trade; programming language.
 This package supplements the <code>java.sql</code>
 package and, as of the version 1.4 release, is included in the 
 Java Platform, Standard Edition (Java SE&trade;).
@@ -84,7 +84,7 @@
 creates is a connection to that physical data source. 
 <P>
 A logical name for the data source is registered with a naming service that
-uses the Java Naming and Directory Interface<sup><font size=-2>TM</font></sup>  
+uses the Java Naming and Directory Interface&trade;
 (JNDI) API, usually by a system administrator or someone performing the 
 duties of a system administrator. An application can retrieve the
 <code>DataSource</code> object it wants by doing a lookup on the logical
@@ -189,7 +189,7 @@
 <LI>Event Notification 
 <UL>
   <LI><code>RowSetListener</code><br>
-A <code>RowSet</code> object is a JavaBeans<sup><font size=-2>TM</font></sup>
+A <code>RowSet</code> object is a JavaBeans&trade;
 component because it has properties and participates in the JavaBeans
 event notification mechanism. The <code>RowSetListener</code> interface 
 is implemented by a component that wants to be notified about events that 
--- a/jdk/src/java.xml.crypto/share/classes/com/sun/org/apache/xml/internal/security/utils/IgnoreAllErrorHandler.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.xml.crypto/share/classes/com/sun/org/apache/xml/internal/security/utils/IgnoreAllErrorHandler.java	Wed Jul 05 20:35:10 2017 +0200
@@ -35,19 +35,30 @@
 public class IgnoreAllErrorHandler implements ErrorHandler {
 
     /** {@link org.apache.commons.logging} logging facility */
-    private static java.util.logging.Logger log =
+    private static final java.util.logging.Logger log =
         java.util.logging.Logger.getLogger(IgnoreAllErrorHandler.class.getName());
 
     /** Field throwExceptions */
-    private static final boolean warnOnExceptions =
-        System.getProperty("com.sun.org.apache.xml.internal.security.test.warn.on.exceptions", "false").equals("true");
+    private static final boolean warnOnExceptions = getProperty(
+            "com.sun.org.apache.xml.internal.security.test.warn.on.exceptions");
 
     /** Field throwExceptions           */
-    private static final boolean throwExceptions =
-        System.getProperty("com.sun.org.apache.xml.internal.security.test.throw.exceptions", "false").equals("true");
+    private static final boolean throwExceptions = getProperty(
+            "com.sun.org.apache.xml.internal.security.test.throw.exceptions");
+
+    private static boolean getProperty(String name) {
+        return java.security.AccessController.doPrivileged(
+                new java.security.PrivilegedAction<Boolean>() {
 
+                    @Override
+                    public Boolean run() {
+                        return Boolean.getBoolean(name);
+                    }
+                });
+    }
 
     /** @inheritDoc */
+    @Override
     public void warning(SAXParseException ex) throws SAXException {
         if (IgnoreAllErrorHandler.warnOnExceptions) {
             log.log(java.util.logging.Level.WARNING, "", ex);
@@ -59,6 +70,7 @@
 
 
     /** @inheritDoc */
+    @Override
     public void error(SAXParseException ex) throws SAXException {
         if (IgnoreAllErrorHandler.warnOnExceptions) {
             log.log(java.util.logging.Level.SEVERE, "", ex);
@@ -70,6 +82,7 @@
 
 
     /** @inheritDoc */
+    @Override
     public void fatalError(SAXParseException ex) throws SAXException {
         if (IgnoreAllErrorHandler.warnOnExceptions) {
             log.log(java.util.logging.Level.WARNING, "", ex);
--- a/jdk/src/java.xml.crypto/share/classes/org/jcp/xml/dsig/internal/dom/DOMKeyValue.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/java.xml.crypto/share/classes/org/jcp/xml/dsig/internal/dom/DOMKeyValue.java	Wed Jul 05 20:35:10 2017 +0200
@@ -326,32 +326,54 @@
         private KeyFactory eckf;
         private ECParameterSpec ecParams;
 
-        // The supported curve, secp256r1
-        private static final Curve SECP256R1;
-        static {
-            final String name, oid, sfield, a, b, x, y, n;
-            name = "secp256r1 [NIST P-256, X9.62 prime256v1]";
-            oid  = "1.2.840.10045.3.1.7";
-            sfield =
-             "FFFFFFFF00000001000000000000000000000000FFFFFFFFFFFFFFFFFFFFFFFF";
-            a =
-             "FFFFFFFF00000001000000000000000000000000FFFFFFFFFFFFFFFFFFFFFFFC";
-            b =
-             "5AC635D8AA3A93E7B3EBBD55769886BC651D06B0CC53B0F63BCE3C3E27D2604B";
-            x =
-             "6B17D1F2E12C4247F8BCE6E563A440F277037D812DEB33A0F4A13945D898C296";
-            y =
-             "4FE342E2FE1A7F9B8EE7EB4A7C0F9E162BCE33576B315ECECBB6406837BF51F5";
-            n =
-             "FFFFFFFF00000000FFFFFFFFFFFFFFFFBCE6FAADA7179E84F3B9CAC2FC632551";
-            final int h = 1;
+        /* Supported curve, secp256r1 */
+        private static final Curve SECP256R1 = initializeCurve(
+            "secp256r1 [NIST P-256, X9.62 prime256v1]",
+            "1.2.840.10045.3.1.7",
+            "FFFFFFFF00000001000000000000000000000000FFFFFFFFFFFFFFFFFFFFFFFF",
+            "FFFFFFFF00000001000000000000000000000000FFFFFFFFFFFFFFFFFFFFFFFC",
+            "5AC635D8AA3A93E7B3EBBD55769886BC651D06B0CC53B0F63BCE3C3E27D2604B",
+            "6B17D1F2E12C4247F8BCE6E563A440F277037D812DEB33A0F4A13945D898C296",
+            "4FE342E2FE1A7F9B8EE7EB4A7C0F9E162BCE33576B315ECECBB6406837BF51F5",
+            "FFFFFFFF00000000FFFFFFFFFFFFFFFFBCE6FAADA7179E84F3B9CAC2FC632551",
+            1
+        );
 
+        /* Supported curve secp384r1 */
+        private static final Curve SECP384R1 = initializeCurve(
+            "secp384r1 [NIST P-384]",
+            "1.3.132.0.34",
+            "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFFFF0000000000000000FFFFFFFF",
+            "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFFFF0000000000000000FFFFFFFC",
+            "B3312FA7E23EE7E4988E056BE3F82D19181D9C6EFE8141120314088F5013875AC656398D8A2ED19D2A85C8EDD3EC2AEF",
+            "AA87CA22BE8B05378EB1C71EF320AD746E1D3B628BA79B9859F741E082542A385502F25DBF55296C3A545E3872760AB7",
+            "3617DE4A96262C6F5D9E98BF9292DC29F8F41DBD289A147CE9DA3113B5F0B8C00A60B1CE1D7E819D7A431D7C90EA0E5F",
+            "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFC7634D81F4372DDF581A0DB248B0A77AECEC196ACCC52973",
+            1
+        );
+
+        /* Supported curve secp521r1 */
+        private static final Curve SECP521R1 = initializeCurve(
+            "secp521r1 [NIST P-521]",
+            "1.3.132.0.35",
+            "01FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF",
+            "01FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFC",
+            "0051953EB9618E1C9A1F929A21A0B68540EEA2DA725B99B315F3B8B489918EF109E156193951EC7E937B1652C0BD3BB1BF073573DF883D2C34F1EF451FD46B503F00",
+            "00C6858E06B70404E9CD9E3ECB662395B4429C648139053FB521F828AF606B4D3DBAA14B5E77EFE75928FE1DC127A2FFA8DE3348B3C1856A429BF97E7E31C2E5BD66",
+            "011839296A789A3BC0045C8A5FB42C7D1BD998F54449579B446817AFBD17273E662C97EE72995EF42640C550B9013FAD0761353C7086A272C24088BE94769FD16650",
+            "01FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFA51868783BF2F966B7FCC0148F709A5D03BB5C9B8899C47AEBB6FB71E91386409",
+            1
+        );
+
+        private static Curve initializeCurve(String name, String oid,
+                String sfield, String a, String b,
+                String x, String y, String n, int h) {
             BigInteger p = bigInt(sfield);
             ECField field = new ECFieldFp(p);
             EllipticCurve curve = new EllipticCurve(field, bigInt(a),
                                                     bigInt(b));
             ECPoint g = new ECPoint(bigInt(x), bigInt(y));
-            SECP256R1 = new Curve(name, oid, curve, g, bigInt(n), h);
+            return new Curve(name, oid, curve, g, bigInt(n), h);
         }
 
         EC(PublicKey key) throws KeyException {
@@ -413,24 +435,45 @@
         }
 
         private static String getCurveOid(ECParameterSpec params) {
-            // Check that the params represent the secp256r1 curve
-            // If so, return the object identifier of the curve
+            // Check that the params represent one of the supported
+            // curves. If there is a match, return the object identifier
+            // of the curve.
+            Curve match;
+            if (matchCurve(params, SECP256R1)) {
+                match = SECP256R1;
+            } else if (matchCurve(params, SECP384R1)) {
+                match = SECP384R1;
+            } else if (matchCurve(params, SECP521R1)) {
+                match = SECP521R1;
+            } else {
+                return null;
+            }
+            return match.getObjectId();
+        }
+
+        private static boolean matchCurve(ECParameterSpec params, Curve curve) {
             int fieldSize = params.getCurve().getField().getFieldSize();
-            if (SECP256R1.getCurve().getField().getFieldSize() == fieldSize
-                && SECP256R1.getCurve().equals(params.getCurve())
-                && SECP256R1.getGenerator().equals(params.getGenerator())
-                && SECP256R1.getOrder().equals(params.getOrder())
-                && SECP256R1.getCofactor() == params.getCofactor()) {
-                return SECP256R1.getObjectId();
+            if (curve.getCurve().getField().getFieldSize() == fieldSize
+                && curve.getCurve().equals(params.getCurve())
+                && curve.getGenerator().equals(params.getGenerator())
+                && curve.getOrder().equals(params.getOrder())
+                && curve.getCofactor() == params.getCofactor()) {
+                return true;
+            } else {
+                return false;
             }
-            return null;
         }
 
         private static ECParameterSpec getECParameterSpec(String oid) {
             if (oid.equals(SECP256R1.getObjectId())) {
                 return SECP256R1;
+            } else if (oid.equals(SECP384R1.getObjectId())) {
+                return SECP384R1;
+            } else if (oid.equals(SECP521R1.getObjectId())) {
+                return SECP521R1;
+            } else {
+                return null;
             }
-            return null;
         }
 
         void marshalPublicKey(Node parent, Document doc, String dsPrefix,
--- a/jdk/src/jdk.attach/share/classes/com/sun/tools/attach/package-info.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/jdk.attach/share/classes/com/sun/tools/attach/package-info.java	Wed Jul 05 20:35:10 2017 +0200
@@ -24,8 +24,7 @@
  */
 
 /**
- * Provides the API to attach to a Java<sup><font size=-2>TM</font></sup>
- * virtual machine.
+ * Provides the API to attach to a Java&trade; virtual machine.
  * <p>
  * A tool, written in the Java Language, uses this API to attach to a target
  * virtual machine (VM) and load its tool agent into the target VM. For
--- a/jdk/src/jdk.attach/share/classes/com/sun/tools/attach/spi/AttachProvider.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/jdk.attach/share/classes/com/sun/tools/attach/spi/AttachProvider.java	Wed Jul 05 20:35:10 2017 +0200
@@ -241,7 +241,7 @@
      * (using the zero-arg constructor) at the first invocation of this method.
      * The list returned by the first invocation of this method is the list
      * of providers. Subsequent invocations of this method return a list of the same
-     * providers. The list is unmodifable.
+     * providers. The list is unmodifiable.
      *
      * @return  A list of the installed attach providers.
      */
@@ -264,8 +264,8 @@
                             ThreadDeath td = (ThreadDeath)t;
                             throw td;
                         }
-                        // Ignore errors and exceptions
-                        System.err.println(t);
+                        // Log errors and exceptions since we cannot return them
+                        t.printStackTrace();
                     }
                 }
             }
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/Main.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,212 +0,0 @@
-/*
- * Copyright (c) 2005, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat;
-
-import java.io.IOException;
-import java.io.File;
-
-import com.sun.tools.hat.internal.model.Snapshot;
-import com.sun.tools.hat.internal.model.ReachableExcludesImpl;
-import com.sun.tools.hat.internal.server.QueryListener;
-
-/**
- *
- * @author      Bill Foote
- */
-
-
-public class Main {
-
-    private static String VERSION_STRING = "jhat version 2.0";
-
-    private static void usage(String message) {
-        if ( message != null ) {
-            System.err.println("ERROR: " + message);
-        }
-        System.err.println("Usage:  jhat [-stack <bool>] [-refs <bool>] [-port <port>] [-baseline <file>] [-debug <int>] [-version] [-h|-help] <file>");
-        System.err.println();
-        System.err.println("\t-J<flag>          Pass <flag> directly to the runtime system. For");
-        System.err.println("\t\t\t  example, -J-mx512m to use a maximum heap size of 512MB");
-        System.err.println("\t-stack false:     Turn off tracking object allocation call stack.");
-        System.err.println("\t-refs false:      Turn off tracking of references to objects");
-        System.err.println("\t-port <port>:     Set the port for the HTTP server.  Defaults to 7000");
-        System.err.println("\t-exclude <file>:  Specify a file that lists data members that should");
-        System.err.println("\t\t\t  be excluded from the reachableFrom query.");
-        System.err.println("\t-baseline <file>: Specify a baseline object dump.  Objects in");
-        System.err.println("\t\t\t  both heap dumps with the same ID and same class will");
-        System.err.println("\t\t\t  be marked as not being \"new\".");
-        System.err.println("\t-debug <int>:     Set debug level.");
-        System.err.println("\t\t\t    0:  No debug output");
-        System.err.println("\t\t\t    1:  Debug hprof file parsing");
-        System.err.println("\t\t\t    2:  Debug hprof file parsing, no server");
-        System.err.println("\t-version          Report version number");
-        System.err.println("\t-h|-help          Print this help and exit");
-        System.err.println("\t<file>            The file to read");
-        System.err.println();
-        System.err.println("For a dump file that contains multiple heap dumps,");
-        System.err.println("you may specify which dump in the file");
-        System.err.println("by appending \"#<number>\" to the file name, i.e. \"foo.hprof#3\".");
-        System.err.println();
-        System.err.println("All boolean options default to \"true\"");
-        System.exit(1);
-    }
-
-    //
-    // Convert s to a boolean.  If it's invalid, abort the program.
-    //
-    private static boolean booleanValue(String s) {
-        if ("true".equalsIgnoreCase(s)) {
-            return true;
-        } else if ("false".equalsIgnoreCase(s)) {
-            return false;
-        } else {
-            usage("Boolean value must be true or false");
-            return false;       // Never happens
-        }
-    }
-
-    public static void main(String[] args) {
-        if (args.length < 1) {
-            usage("No arguments supplied");
-        }
-
-        boolean parseonly = false;
-        int portNumber = 7000;
-        boolean callStack = true;
-        boolean calculateRefs = true;
-        String baselineDump = null;
-        String excludeFileName = null;
-        int debugLevel = 0;
-        for (int i = 0; ; i += 2) {
-            if (i > (args.length - 1)) {
-                usage("Option parsing error");
-            }
-            if ("-version".equals(args[i])) {
-                System.out.print(VERSION_STRING);
-                System.out.println(" (java version " + System.getProperty("java.version") + ")");
-                System.exit(0);
-            }
-
-            if ("-h".equals(args[i]) || "-help".equals(args[i])) {
-                usage(null);
-            }
-
-            if (i == (args.length - 1)) {
-                break;
-            }
-            String key = args[i];
-            String value = args[i+1];
-            if ("-stack".equals(key)) {
-                callStack = booleanValue(value);
-            } else if ("-refs".equals(key)) {
-                calculateRefs = booleanValue(value);
-            } else if ("-port".equals(key)) {
-                portNumber = Integer.parseInt(value, 10);
-            } else if ("-exclude".equals(key)) {
-                excludeFileName = value;
-            } else if ("-baseline".equals(key)) {
-                baselineDump = value;
-            } else if ("-debug".equals(key)) {
-                debugLevel = Integer.parseInt(value, 10);
-            } else if ("-parseonly".equals(key)) {
-                // Undocumented option. To be used for testing purpose only
-                parseonly = booleanValue(value);
-            }
-        }
-        String fileName = args[args.length - 1];
-        Snapshot model = null;
-        File excludeFile = null;
-        if (excludeFileName != null) {
-            excludeFile = new File(excludeFileName);
-            if (!excludeFile.exists()) {
-                System.out.println("Exclude file " + excludeFile
-                                    + " does not exist.  Aborting.");
-                System.exit(1);
-            }
-        }
-
-        System.out.println("Reading from " + fileName + "...");
-        try {
-            model = com.sun.tools.hat.internal.parser.Reader.readFile(fileName, callStack, debugLevel);
-        } catch (IOException ex) {
-            ex.printStackTrace();
-            System.exit(1);
-        } catch (RuntimeException ex) {
-            ex.printStackTrace();
-            System.exit(1);
-        }
-        System.out.println("Snapshot read, resolving...");
-        model.resolve(calculateRefs);
-        System.out.println("Snapshot resolved.");
-
-        if (excludeFile != null) {
-            model.setReachableExcludes(new ReachableExcludesImpl(excludeFile));
-        }
-
-        if (baselineDump != null) {
-            System.out.println("Reading baseline snapshot...");
-            Snapshot baseline = null;
-            try {
-                baseline = com.sun.tools.hat.internal.parser.Reader.readFile(baselineDump, false,
-                                                      debugLevel);
-            } catch (IOException ex) {
-                ex.printStackTrace();
-                System.exit(1);
-            } catch (RuntimeException ex) {
-                ex.printStackTrace();
-                System.exit(1);
-            }
-            baseline.resolve(false);
-            System.out.println("Discovering new objects...");
-            model.markNewRelativeTo(baseline);
-            baseline = null;    // Guard against conservative GC
-        }
-        if ( debugLevel == 2 ) {
-            System.out.println("No server, -debug 2 was used.");
-            System.exit(0);
-        }
-
-        if (parseonly) {
-            // do not start web server.
-            System.out.println("-parseonly is true, exiting..");
-            System.exit(0);
-        }
-
-        QueryListener listener = new QueryListener(portNumber);
-        listener.setModel(model);
-        Thread t = new Thread(listener, "Query Listener");
-        t.setPriority(Thread.NORM_PRIORITY+1);
-        t.start();
-        System.out.println("Started HTTP server on port " + portNumber);
-        System.out.println("Server is ready.");
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/AbstractJavaHeapObjectVisitor.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,60 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-/**
- * A visitor for a JavaThing.  @see JavaObject#visitReferencedObjects()
- *
- */
-
-
-abstract public class AbstractJavaHeapObjectVisitor
-                implements JavaHeapObjectVisitor {
-    abstract public void visit(JavaHeapObject other);
-
-    /**
-     * Should the given field be excluded from the set of things visited?
-     * @return true if it should.
-     */
-    public boolean exclude(JavaClass clazz, JavaField f) {
-        return false;
-    }
-
-    /**
-     * @return true iff exclude might ever return true
-     */
-    public boolean mightExclude() {
-        return false;
-    }
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/ArrayTypeCodes.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,50 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-/**
- * Primitive array type codes as defined by VM specification.
- *
- */
-public interface ArrayTypeCodes {
-    // Typecodes for array elements.
-    // Refer to newarray instruction in VM Spec.
-    public static final int T_BOOLEAN = 4;
-    public static final int T_CHAR    = 5;
-    public static final int T_FLOAT   = 6;
-    public static final int T_DOUBLE  = 7;
-    public static final int T_BYTE    = 8;
-    public static final int T_SHORT   = 9;
-    public static final int T_INT     = 10;
-    public static final int T_LONG    = 11;
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/HackJavaValue.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,65 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-/**
- * This is used to represent values that the program doesn't really understand.
- * This includes the null vlaue, and unresolved references (which shouldn't
- * happen in well-formed hprof files).
- *
- *
- * @author      Bill Foote
- */
-
-
-
-
-public class HackJavaValue extends JavaValue {
-
-    private String value;
-    private int size;
-
-    public HackJavaValue(String value, int size) {
-        this.value = value;
-        this.size = size;
-    }
-
-    public String toString() {
-        return value;
-    }
-
-    public int getSize() {
-        return size;
-    }
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaBoolean.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,54 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-/**
- * Represents a boolean (i.e. a boolean field in an instance).
- *
- * @author      Bill Foote
- */
-
-
-public class JavaBoolean extends JavaValue {
-
-    boolean value;
-
-    public JavaBoolean(boolean value) {
-        this.value = value;
-    }
-
-    public String toString() {
-        return "" + value;
-    }
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaByte.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,54 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-/**
- * Represents an byte (i.e. a byte field in an instance).
- *
- * @author      Bill Foote
- */
-
-
-public class JavaByte extends JavaValue {
-
-    byte value;
-
-    public JavaByte(byte value) {
-        this.value = value;
-    }
-
-    public String toString() {
-        return "0x" + Integer.toString(((int) value) & 0xff, 16);
-    }
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaChar.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,54 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-/**
- * Represents a char (i.e. a char field in an instance).
- *
- * @author      Bill Foote
- */
-
-
-public class JavaChar extends JavaValue {
-
-    char value;
-
-    public JavaChar(char value) {
-        this.value = value;
-    }
-
-    public String toString() {
-        return "" + value;
-    }
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaClass.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,503 +0,0 @@
-/*
- * Copyright (c) 1997, 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-import java.util.Vector;
-import java.util.Enumeration;
-import com.sun.tools.hat.internal.util.CompositeEnumeration;
-import com.sun.tools.hat.internal.parser.ReadBuffer;
-
-/**
- *
- * @author      Bill Foote
- */
-
-
-public class JavaClass extends JavaHeapObject {
-    // my id
-    private long id;
-    // my name
-    private String name;
-
-    // These are JavaObjectRef before resolve
-    private JavaThing superclass;
-    private JavaThing loader;
-    private JavaThing signers;
-    private JavaThing protectionDomain;
-
-    // non-static fields
-    private JavaField[] fields;
-    // static fields
-    private JavaStatic[] statics;
-
-    private static final JavaClass[] EMPTY_CLASS_ARRAY = new JavaClass[0];
-    // my subclasses
-    private JavaClass[] subclasses = EMPTY_CLASS_ARRAY;
-
-    // my instances
-    private Vector<JavaHeapObject> instances = new Vector<JavaHeapObject>();
-
-    // Who I belong to.  Set on resolve.
-    private Snapshot mySnapshot;
-
-    // Size of an instance, including VM overhead
-    private int instanceSize;
-    // Total number of fields including inherited ones
-    private int totalNumFields;
-
-
-    public JavaClass(long id, String name, long superclassId, long loaderId,
-                     long signersId, long protDomainId,
-                     JavaField[] fields, JavaStatic[] statics,
-                     int instanceSize) {
-        this.id = id;
-        this.name = name;
-        this.superclass = new JavaObjectRef(superclassId);
-        this.loader = new JavaObjectRef(loaderId);
-        this.signers = new JavaObjectRef(signersId);
-        this.protectionDomain = new JavaObjectRef(protDomainId);
-        this.fields = fields;
-        this.statics = statics;
-        this.instanceSize = instanceSize;
-    }
-
-    public JavaClass(String name, long superclassId, long loaderId,
-                     long signersId, long protDomainId,
-                     JavaField[] fields, JavaStatic[] statics,
-                     int instanceSize) {
-        this(-1L, name, superclassId, loaderId, signersId,
-             protDomainId, fields, statics, instanceSize);
-    }
-
-    public final JavaClass getClazz() {
-        return mySnapshot.getJavaLangClass();
-    }
-
-    public final int getIdentifierSize() {
-        return mySnapshot.getIdentifierSize();
-    }
-
-    public final int getMinimumObjectSize() {
-        return mySnapshot.getMinimumObjectSize();
-    }
-
-    public void resolve(Snapshot snapshot) {
-        if (mySnapshot != null) {
-            return;
-        }
-        mySnapshot = snapshot;
-        resolveSuperclass(snapshot);
-        if (superclass != null) {
-            ((JavaClass) superclass).addSubclass(this);
-        }
-
-        loader  = loader.dereference(snapshot, null);
-        signers  = signers.dereference(snapshot, null);
-        protectionDomain  = protectionDomain.dereference(snapshot, null);
-
-        for (int i = 0; i < statics.length; i++) {
-            statics[i].resolve(this, snapshot);
-        }
-        snapshot.getJavaLangClass().addInstance(this);
-        super.resolve(snapshot);
-        return;
-    }
-
-    /**
-     * Resolve our superclass.  This might be called well before
-     * all instances are available (like when reading deferred
-     * instances in a 1.2 dump file :-)  Calling this is sufficient
-     * to be able to explore this class' fields.
-     */
-    public void resolveSuperclass(Snapshot snapshot) {
-        if (superclass == null) {
-            // We must be java.lang.Object, so we have no superclass.
-        } else {
-            totalNumFields = fields.length;
-            superclass = superclass.dereference(snapshot, null);
-            if (superclass == snapshot.getNullThing()) {
-                superclass = null;
-            } else {
-                try {
-                    JavaClass sc = (JavaClass) superclass;
-                    sc.resolveSuperclass(snapshot);
-                    totalNumFields += sc.totalNumFields;
-                } catch (ClassCastException ex) {
-                    System.out.println("Warning!  Superclass of " + name + " is " + superclass);
-                    superclass = null;
-                }
-            }
-        }
-    }
-
-    public boolean isString() {
-        return mySnapshot.getJavaLangString() == this;
-    }
-
-    public boolean isClassLoader() {
-        return mySnapshot.getJavaLangClassLoader().isAssignableFrom(this);
-    }
-
-    /**
-     * Get a numbered field from this class
-     */
-    public JavaField getField(int i) {
-        if (i < 0 || i >= fields.length) {
-            throw new Error("No field " + i + " for " + name);
-        }
-        return fields[i];
-    }
-
-    /**
-     * Get the total number of fields that are part of an instance of
-     * this class.  That is, include superclasses.
-     */
-    public int getNumFieldsForInstance() {
-        return totalNumFields;
-    }
-
-    /**
-     * Get a numbered field from all the fields that are part of instance
-     * of this class.  That is, include superclasses.
-     */
-    public JavaField getFieldForInstance(int i) {
-        if (superclass != null) {
-            JavaClass sc = (JavaClass) superclass;
-            if (i < sc.totalNumFields) {
-                return sc.getFieldForInstance(i);
-            }
-            i -= sc.totalNumFields;
-        }
-        return getField(i);
-    }
-
-    /**
-     * Get the class responsible for field i, where i is a field number that
-     * could be passed into getFieldForInstance.
-     *
-     * @see JavaClass.getFieldForInstance()
-     */
-    public JavaClass getClassForField(int i) {
-        if (superclass != null) {
-            JavaClass sc = (JavaClass) superclass;
-            if (i < sc.totalNumFields) {
-                return sc.getClassForField(i);
-            }
-        }
-        return this;
-    }
-
-    public long getId() {
-        return id;
-    }
-
-    public String getName() {
-        return name;
-    }
-
-    public boolean isArray() {
-        return name.indexOf('[') != -1;
-    }
-
-    public Enumeration<JavaHeapObject> getInstances(boolean includeSubclasses) {
-        if (includeSubclasses) {
-            Enumeration<JavaHeapObject> res = instances.elements();
-            for (int i = 0; i < subclasses.length; i++) {
-                res = new CompositeEnumeration(res,
-                              subclasses[i].getInstances(true));
-            }
-            return res;
-        } else {
-            return instances.elements();
-        }
-    }
-
-    /**
-     * @return a count of the instances of this class
-     */
-    public int getInstancesCount(boolean includeSubclasses) {
-        int result = instances.size();
-        if (includeSubclasses) {
-            for (int i = 0; i < subclasses.length; i++) {
-                result += subclasses[i].getInstancesCount(includeSubclasses);
-            }
-        }
-        return result;
-    }
-
-    public JavaClass[] getSubclasses() {
-        return subclasses;
-    }
-
-    /**
-     * This can only safely be called after resolve()
-     */
-    public JavaClass getSuperclass() {
-        return (JavaClass) superclass;
-    }
-
-    /**
-     * This can only safely be called after resolve()
-     */
-    public JavaThing getLoader() {
-        return loader;
-    }
-
-    /**
-     * This can only safely be called after resolve()
-     */
-    public boolean isBootstrap() {
-        return loader == mySnapshot.getNullThing();
-    }
-
-    /**
-     * This can only safely be called after resolve()
-     */
-    public JavaThing getSigners() {
-        return signers;
-    }
-
-    /**
-     * This can only safely be called after resolve()
-     */
-    public JavaThing getProtectionDomain() {
-        return protectionDomain;
-    }
-
-    public JavaField[] getFields() {
-        return fields;
-    }
-
-    /**
-     * Includes superclass fields
-     */
-    public JavaField[] getFieldsForInstance() {
-        Vector<JavaField> v = new Vector<JavaField>();
-        addFields(v);
-        JavaField[] result = new JavaField[v.size()];
-        for (int i = 0; i < v.size(); i++) {
-            result[i] =  v.elementAt(i);
-        }
-        return result;
-    }
-
-
-    public JavaStatic[] getStatics() {
-        return statics;
-    }
-
-    // returns value of static field of given name
-    public JavaThing getStaticField(String name) {
-        for (int i = 0; i < statics.length; i++) {
-            JavaStatic s = statics[i];
-            if (s.getField().getName().equals(name)) {
-                return s.getValue();
-            }
-        }
-        return null;
-    }
-
-    public String toString() {
-        return "class " + name;
-    }
-
-    public int compareTo(JavaThing other) {
-        if (other instanceof JavaClass) {
-            return name.compareTo(((JavaClass) other).name);
-        }
-        return super.compareTo(other);
-    }
-
-
-    /**
-     * @return true iff a variable of type this is assignable from an instance
-     *          of other
-     */
-    public boolean isAssignableFrom(JavaClass other) {
-        if (this == other) {
-            return true;
-        } else if (other == null) {
-            return false;
-        } else {
-            return isAssignableFrom((JavaClass) other.superclass);
-            // Trivial tail recursion:  I have faith in javac.
-        }
-    }
-
-    /**
-     * Describe the reference that this thing has to target.  This will only
-     * be called if target is in the array returned by getChildrenForRootset.
-     */
-     public String describeReferenceTo(JavaThing target, Snapshot ss) {
-        for (int i = 0; i < statics.length; i++) {
-            JavaField f = statics[i].getField();
-            if (f.hasId()) {
-                JavaThing other = statics[i].getValue();
-                if (other == target) {
-                    return "static field " + f.getName();
-                }
-            }
-        }
-        return super.describeReferenceTo(target, ss);
-    }
-
-    /**
-     * @return the size of an instance of this class.  Gives 0 for an array
-     *          type.
-     */
-    public int getInstanceSize() {
-        return instanceSize + mySnapshot.getMinimumObjectSize();
-    }
-
-
-    /**
-     * @return The size of all instances of this class.  Correctly handles
-     *          arrays.
-     */
-    public long getTotalInstanceSize() {
-        int count = instances.size();
-        if (count == 0 || !isArray()) {
-            return count * instanceSize;
-        }
-
-        // array class and non-zero count, we have to
-        // get the size of each instance and sum it
-        long result = 0;
-        for (int i = 0; i < count; i++) {
-            JavaThing t = (JavaThing) instances.elementAt(i);
-            result += t.getSize();
-        }
-        return result;
-    }
-
-    /**
-     * @return the size of this object
-     */
-    public int getSize() {
-        JavaClass cl = mySnapshot.getJavaLangClass();
-        if (cl == null) {
-            return 0;
-        } else {
-            return cl.getInstanceSize();
-        }
-    }
-
-    public void visitReferencedObjects(JavaHeapObjectVisitor v) {
-        super.visitReferencedObjects(v);
-        JavaHeapObject sc = getSuperclass();
-        if (sc != null) v.visit(getSuperclass());
-
-        JavaThing other;
-        other = getLoader();
-        if (other instanceof JavaHeapObject) {
-            v.visit((JavaHeapObject)other);
-        }
-        other = getSigners();
-        if (other instanceof JavaHeapObject) {
-            v.visit((JavaHeapObject)other);
-        }
-        other = getProtectionDomain();
-        if (other instanceof JavaHeapObject) {
-            v.visit((JavaHeapObject)other);
-        }
-
-        for (int i = 0; i < statics.length; i++) {
-            JavaField f = statics[i].getField();
-            if (!v.exclude(this, f) && f.hasId()) {
-                other = statics[i].getValue();
-                if (other instanceof JavaHeapObject) {
-                    v.visit((JavaHeapObject) other);
-                }
-            }
-        }
-    }
-
-    // package-privates below this point
-    final ReadBuffer getReadBuffer() {
-        return mySnapshot.getReadBuffer();
-    }
-
-    final void setNew(JavaHeapObject obj, boolean flag) {
-        mySnapshot.setNew(obj, flag);
-    }
-
-    final boolean isNew(JavaHeapObject obj) {
-        return mySnapshot.isNew(obj);
-    }
-
-    final StackTrace getSiteTrace(JavaHeapObject obj) {
-        return mySnapshot.getSiteTrace(obj);
-    }
-
-    final void addReferenceFromRoot(Root root, JavaHeapObject obj) {
-        mySnapshot.addReferenceFromRoot(root, obj);
-    }
-
-    final Root getRoot(JavaHeapObject obj) {
-        return mySnapshot.getRoot(obj);
-    }
-
-    final Snapshot getSnapshot() {
-        return mySnapshot;
-    }
-
-    void addInstance(JavaHeapObject inst) {
-        instances.addElement(inst);
-    }
-
-    // Internals only below this point
-    private void addFields(Vector<JavaField> v) {
-        if (superclass != null) {
-            ((JavaClass) superclass).addFields(v);
-        }
-        for (int i = 0; i < fields.length; i++) {
-            v.addElement(fields[i]);
-        }
-    }
-
-    private void addSubclassInstances(Vector<JavaHeapObject> v) {
-        for (int i = 0; i < subclasses.length; i++) {
-            subclasses[i].addSubclassInstances(v);
-        }
-        for (int i = 0; i < instances.size(); i++) {
-            v.addElement(instances.elementAt(i));
-        }
-    }
-
-    private void addSubclass(JavaClass sub) {
-        JavaClass newValue[] = new JavaClass[subclasses.length + 1];
-        System.arraycopy(subclasses, 0, newValue, 0, subclasses.length);
-        newValue[subclasses.length] = sub;
-        subclasses = newValue;
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaDouble.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,53 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-/**
- * Represents a double (i.e. a double field in an instance).
- *
- * @author      Bill Foote
- */
-
-
-public class JavaDouble extends JavaValue {
-
-    double value;
-
-    public JavaDouble(double value) {
-        this.value = value;
-    }
-
-    public String toString() {
-        return Double.toString(value);
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaField.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,69 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-
-/**
- *
- * @author      Bill Foote
- */
-
-public class JavaField {
-
-    private String name;
-    private String signature;
-
-    public JavaField(String name, String signature) {
-        this.name = name;
-        this.signature = signature;
-    }
-
-
-    /**
-     * @return true if the type of this field is something that has an ID.
-     *          int fields, for exampe, don't.
-     */
-    public boolean hasId() {
-        char ch = signature.charAt(0);
-        return (ch == '[' || ch == 'L');
-    }
-
-    public String getName() {
-        return name;
-    }
-
-    public String getSignature() {
-        return signature;
-    }
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaFloat.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,53 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-/**
- * Represents a float (i.e. a float field in an instance).
- *
- * @author      Bill Foote
- */
-
-
-public class JavaFloat extends JavaValue {
-
-    float value;
-
-    public JavaFloat(float value) {
-        this.value = value;
-    }
-
-    public String toString() {
-        return Float.toString(value);
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaHeapObject.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,207 +0,0 @@
-/*
- * Copyright (c) 1997, 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-import java.util.Enumeration;
-import java.util.HashMap;
-import java.util.Map;
-import com.sun.tools.hat.internal.util.Misc;
-
-
-/**
- *
- * @author      Bill Foote
- */
-
-/**
- * Represents an object that's allocated out of the Java heap.  It occupies
- * memory in the VM, and is the sort of thing that in a JDK 1.1 VM had
- * a handle.  It can be a
- * JavaClass, a JavaObjectArray, a JavaValueArray or a JavaObject.
- */
-
-public abstract class JavaHeapObject extends JavaThing {
-
-    //
-    // Who we refer to.  This is heavily optimized for space, because it's
-    // well worth trading a bit of speed for less swapping.
-    // referers and referersLen go through two phases:  Building and
-    // resolved.  When building, referers might have duplicates, but can
-    // be appended to.  When resolved, referers has no duplicates or
-    // empty slots.
-    //
-    private JavaThing[] referers = null;
-    private int referersLen = 0;        // -1 when resolved
-
-    public abstract JavaClass getClazz();
-    public abstract int getSize();
-    public abstract long getId();
-
-    /**
-     * Do any initialization this thing needs after its data is read in.
-     * Subclasses that override this should call super.resolve().
-     */
-    public void resolve(Snapshot snapshot) {
-        StackTrace trace = snapshot.getSiteTrace(this);
-        if (trace != null) {
-            trace.resolve(snapshot);
-        }
-    }
-
-    //
-    //  Eliminate duplicates from referers, and size the array exactly.
-    // This sets us up to answer queries.  See the comments around the
-    // referers data member for details.
-    //
-    void setupReferers() {
-        if (referersLen > 1) {
-            // Copy referers to map, screening out duplicates
-            Map<JavaThing, JavaThing> map = new HashMap<JavaThing, JavaThing>();
-            for (int i = 0; i < referersLen; i++) {
-                if (map.get(referers[i]) == null) {
-                    map.put(referers[i], referers[i]);
-                }
-            }
-
-            // Now copy into the array
-            referers = new JavaThing[map.size()];
-            map.keySet().toArray(referers);
-        }
-        referersLen = -1;
-    }
-
-
-    /**
-     * @return the id of this thing as hex string
-     */
-    public String getIdString() {
-        return Misc.toHex(getId());
-    }
-
-    public String toString() {
-        return getClazz().getName() + "@" + getIdString();
-    }
-
-    /**
-     * @return the StackTrace of the point of allocation of this object,
-     *          or null if unknown
-     */
-    public StackTrace getAllocatedFrom() {
-        return getClazz().getSiteTrace(this);
-    }
-
-    public boolean isNew() {
-        return getClazz().isNew(this);
-    }
-
-    void setNew(boolean flag) {
-        getClazz().setNew(this, flag);
-    }
-
-    /**
-     * Tell the visitor about all of the objects we refer to
-     */
-    public void visitReferencedObjects(JavaHeapObjectVisitor v) {
-        v.visit(getClazz());
-    }
-
-    void addReferenceFrom(JavaHeapObject other) {
-        if (referersLen == 0) {
-            referers = new JavaThing[1];        // It was null
-        } else if (referersLen == referers.length) {
-            JavaThing[] copy = new JavaThing[(3 * (referersLen + 1)) / 2];
-            System.arraycopy(referers, 0, copy, 0, referersLen);
-            referers = copy;
-        }
-        referers[referersLen++] = other;
-        // We just append to referers here.  Measurements have shown that
-        // around 10% to 30% are duplicates, so it's better to just append
-        // blindly and screen out all the duplicates at once.
-    }
-
-    void addReferenceFromRoot(Root r) {
-        getClazz().addReferenceFromRoot(r, this);
-    }
-
-    /**
-     * If the rootset includes this object, return a Root describing one
-     * of the reasons why.
-     */
-    public Root getRoot() {
-        return getClazz().getRoot(this);
-    }
-
-    /**
-     * Tell who refers to us.
-     *
-     * @return an Enumeration of JavaHeapObject instances
-     */
-    public Enumeration<JavaThing> getReferers() {
-        if (referersLen != -1) {
-            throw new RuntimeException("not resolved: " + getIdString());
-        }
-        return new Enumeration<JavaThing>() {
-
-            private int num = 0;
-
-            public boolean hasMoreElements() {
-                return referers != null && num < referers.length;
-            }
-
-            public JavaThing nextElement() {
-                return referers[num++];
-            }
-        };
-    }
-
-    /**
-     * Given other, which the caller promises is in referers, determines if
-     * the reference is only a weak reference.
-     */
-    public boolean refersOnlyWeaklyTo(Snapshot ss, JavaThing other) {
-        return false;
-    }
-
-    /**
-     * Describe the reference that this thing has to target.  This will only
-     * be called if target is in the array returned by getChildrenForRootset.
-     */
-    public String describeReferenceTo(JavaThing target, Snapshot ss) {
-        return "??";
-    }
-
-    public boolean isHeapAllocated() {
-        return true;
-    }
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaHeapObjectVisitor.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,55 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-/**
- * A visitor for a JavaThing.  @see JavaObject#visitReferencedObjects()
- *
- * @author      Bill Foote
- */
-
-
-public interface JavaHeapObjectVisitor {
-    public void visit(JavaHeapObject other);
-
-    /**
-     * Should the given field be excluded from the set of things visited?
-     * @return true if it should.
-     */
-    public boolean exclude(JavaClass clazz, JavaField f);
-
-    /**
-     * @return true iff exclude might ever return true
-     */
-    public boolean mightExclude();
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaInt.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,54 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-/**
- * Represents an integer (i.e. an int field in an instance).
- *
- * @author      Bill Foote
- */
-
-
-public class JavaInt extends JavaValue {
-
-    int value;
-
-    public JavaInt(int value) {
-        this.value = value;
-    }
-
-    public String toString() {
-        return "" + value;
-    }
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaLazyReadObject.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,176 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-import java.io.IOException;
-import com.sun.tools.hat.internal.parser.ReadBuffer;
-
-/*
- * Base class for lazily read Java heap objects.
- */
-public abstract class JavaLazyReadObject extends JavaHeapObject {
-
-    // file offset from which this object data starts
-    private final long offset;
-
-    protected JavaLazyReadObject(long offset) {
-        this.offset = offset;
-    }
-
-    public final int getSize() {
-        return getValueLength() + getClazz().getMinimumObjectSize();
-    }
-
-    protected final long getOffset() {
-        return offset;
-    }
-
-    // return the length of the data for this object
-    protected final int getValueLength() {
-        try {
-            return readValueLength();
-        } catch (IOException exp) {
-            System.err.println("lazy read failed at offset " + offset);
-            exp.printStackTrace();
-            return 0;
-        }
-    }
-
-    // get this object's content as byte array
-    protected final byte[] getValue() {
-        try {
-            return readValue();
-        } catch (IOException exp) {
-            System.err.println("lazy read failed at offset " + offset);
-            exp.printStackTrace();
-            return Snapshot.EMPTY_BYTE_ARRAY;
-        }
-    }
-
-    // get ID of this object
-    public final long getId() {
-        try {
-            ReadBuffer buf = getClazz().getReadBuffer();
-            int idSize = getClazz().getIdentifierSize();
-            if (idSize == 4) {
-                return ((long)buf.getInt(offset)) & Snapshot.SMALL_ID_MASK;
-            } else {
-                return buf.getLong(offset);
-            }
-        } catch (IOException exp) {
-            System.err.println("lazy read failed at offset " + offset);
-            exp.printStackTrace();
-            return -1;
-        }
-    }
-
-    protected abstract int readValueLength() throws IOException;
-    protected abstract byte[] readValue() throws IOException;
-
-    // make Integer or Long for given object ID
-    protected static Number makeId(long id) {
-        if ((id & ~Snapshot.SMALL_ID_MASK) == 0) {
-            return (int)id;
-        } else {
-            return id;
-        }
-    }
-
-    // get ID as long value from Number
-    protected static long getIdValue(Number num) {
-        long id = num.longValue();
-        if (num instanceof Integer) {
-            id &= Snapshot.SMALL_ID_MASK;
-        }
-        return id;
-    }
-
-    // read object ID from given index from given byte array
-    protected final long objectIdAt(int index, byte[] data) {
-        int idSize = getClazz().getIdentifierSize();
-        if (idSize == 4) {
-            return ((long)intAt(index, data)) & Snapshot.SMALL_ID_MASK;
-        } else {
-            return longAt(index, data);
-        }
-    }
-
-    // utility methods to read primitive types from byte array
-    protected static byte byteAt(int index, byte[] value) {
-        return value[index];
-    }
-
-    protected static boolean booleanAt(int index, byte[] value) {
-        return (value[index] & 0xff) == 0? false: true;
-    }
-
-    protected static char charAt(int index, byte[] value) {
-        int b1 = ((int) value[index++] & 0xff);
-        int b2 = ((int) value[index++] & 0xff);
-        return (char) ((b1 << 8) + b2);
-    }
-
-    protected static short shortAt(int index, byte[] value) {
-        int b1 = ((int) value[index++] & 0xff);
-        int b2 = ((int) value[index++] & 0xff);
-        return (short) ((b1 << 8) + b2);
-    }
-
-    protected static int intAt(int index, byte[] value) {
-        int b1 = ((int) value[index++] & 0xff);
-        int b2 = ((int) value[index++] & 0xff);
-        int b3 = ((int) value[index++] & 0xff);
-        int b4 = ((int) value[index++] & 0xff);
-        return ((b1 << 24) + (b2 << 16) + (b3 << 8) + b4);
-    }
-
-    protected static long longAt(int index, byte[] value) {
-        long val = 0;
-        for (int j = 0; j < 8; j++) {
-            val = val << 8;
-            int b = ((int)value[index++]) & 0xff;
-            val |= b;
-        }
-        return val;
-    }
-
-    protected static float floatAt(int index, byte[] value) {
-        int val = intAt(index, value);
-        return Float.intBitsToFloat(val);
-    }
-
-    protected static double doubleAt(int index, byte[] value) {
-        long val = longAt(index, value);
-        return Double.longBitsToDouble(val);
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaLong.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,53 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-/**
- * Represents a long (i.e. a long field in an instance).
- *
- * @author      Bill Foote
- */
-
-
-public class JavaLong extends JavaValue {
-
-    long value;
-
-    public JavaLong(long value) {
-        this.value = value;
-    }
-
-    public String toString() {
-        return Long.toString(value);
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaObject.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,334 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-import java.io.IOException;
-import com.sun.tools.hat.internal.parser.ReadBuffer;
-
-/**
- * Represents Java instance
- *
- * @author      Bill Foote
- */
-public class JavaObject extends JavaLazyReadObject {
-
-    private Object clazz;       // Number before resolve
-                                // JavaClass after resolve
-    /**
-     * Construct a new JavaObject.
-     *
-     * @param classID id of the class object
-     * @param offset The offset of field data
-     */
-    public JavaObject(long classID, long offset) {
-        super(offset);
-        this.clazz = makeId(classID);
-    }
-
-    public void resolve(Snapshot snapshot) {
-        if (clazz instanceof JavaClass) {
-            return;
-        }
-        if (clazz instanceof Number) {
-            long classID = getIdValue((Number)clazz);
-            clazz = snapshot.findThing(classID);
-            if (! (clazz instanceof JavaClass)) {
-                warn("Class " + Long.toHexString(classID) + " not found, " +
-                     "adding fake class!");
-                int length;
-                ReadBuffer buf = snapshot.getReadBuffer();
-                int idSize = snapshot.getIdentifierSize();
-                long lenOffset = getOffset() + 2*idSize + 4;
-                try {
-                    length = buf.getInt(lenOffset);
-                } catch (IOException exp) {
-                    throw new RuntimeException(exp);
-                }
-                clazz = snapshot.addFakeInstanceClass(classID, length);
-            }
-        } else {
-            throw new InternalError("should not reach here");
-        }
-
-        JavaClass cl = (JavaClass) clazz;
-        cl.resolve(snapshot);
-
-        // while resolving, parse fields in verbose mode.
-        // but, getFields calls parseFields in non-verbose mode
-        // to avoid printing warnings repeatedly.
-        parseFields(getValue(), true);
-
-        cl.addInstance(this);
-        super.resolve(snapshot);
-    }
-
-    /**
-     * Are we the same type as other?  We are iff our clazz is the
-     * same type as other's.
-     */
-    public boolean isSameTypeAs(JavaThing other) {
-        if (!(other instanceof JavaObject)) {
-            return false;
-        }
-        JavaObject oo = (JavaObject) other;
-        return getClazz().equals(oo.getClazz());
-    }
-
-    /**
-     * Return our JavaClass object.  This may only be called after resolve.
-     */
-    public JavaClass getClazz() {
-        return (JavaClass) clazz;
-    }
-
-    public JavaThing[] getFields() {
-        // pass false to verbose mode so that dereference
-        // warnings are not printed.
-        return parseFields(getValue(), false);
-    }
-
-    // returns the value of field of given name
-    public JavaThing getField(String name) {
-        JavaThing[] flds = getFields();
-        JavaField[] instFields = getClazz().getFieldsForInstance();
-        for (int i = 0; i < instFields.length; i++) {
-            if (instFields[i].getName().equals(name)) {
-                return flds[i];
-            }
-        }
-        return null;
-    }
-
-    public int compareTo(JavaThing other) {
-        if (other instanceof JavaObject) {
-            JavaObject oo = (JavaObject) other;
-            return getClazz().getName().compareTo(oo.getClazz().getName());
-        }
-        return super.compareTo(other);
-    }
-
-    public void visitReferencedObjects(JavaHeapObjectVisitor v) {
-        super.visitReferencedObjects(v);
-        JavaThing[] flds = getFields();
-        for (int i = 0; i < flds.length; i++) {
-            if (flds[i] != null) {
-                if (v.mightExclude()
-                    && v.exclude(getClazz().getClassForField(i),
-                                 getClazz().getFieldForInstance(i)))
-                {
-                    // skip it
-                } else if (flds[i] instanceof JavaHeapObject) {
-                    v.visit((JavaHeapObject) flds[i]);
-                }
-            }
-        }
-    }
-
-    public boolean refersOnlyWeaklyTo(Snapshot ss, JavaThing other) {
-        if (ss.getWeakReferenceClass() != null) {
-            final int referentFieldIndex = ss.getReferentFieldIndex();
-            if (ss.getWeakReferenceClass().isAssignableFrom(getClazz())) {
-                //
-                // REMIND:  This introduces a dependency on the JDK
-                //      implementation that is undesirable.
-                JavaThing[] flds = getFields();
-                for (int i = 0; i < flds.length; i++) {
-                    if (i != referentFieldIndex && flds[i] == other) {
-                        return false;
-                    }
-                }
-                return true;
-            }
-        }
-        return false;
-    }
-
-    /**
-     * Describe the reference that this thing has to target.  This will only
-     * be called if target is in the array returned by getChildrenForRootset.
-     */
-    public String describeReferenceTo(JavaThing target, Snapshot ss) {
-        JavaThing[] flds = getFields();
-        for (int i = 0; i < flds.length; i++) {
-            if (flds[i] == target) {
-                JavaField f = getClazz().getFieldForInstance(i);
-                return "field " + f.getName();
-            }
-        }
-        return super.describeReferenceTo(target, ss);
-    }
-
-    public String toString() {
-        if (getClazz().isString()) {
-            JavaThing value = getField("value");
-            if (value instanceof JavaValueArray) {
-                return ((JavaValueArray)value).valueString();
-            } else {
-                return "null";
-            }
-        } else {
-            return super.toString();
-        }
-    }
-
-    // Internals only below this point
-
-    /*
-     * Java instance record (HPROF_GC_INSTANCE_DUMP) looks as below:
-     *
-     *     object ID
-     *     stack trace serial number (int)
-     *     class ID
-     *     data length (int)
-     *     byte[length]
-     */
-    protected final int readValueLength() throws IOException {
-        JavaClass cl = getClazz();
-        int idSize = cl.getIdentifierSize();
-        long lengthOffset = getOffset() + 2*idSize + 4;
-        return cl.getReadBuffer().getInt(lengthOffset);
-    }
-
-    protected final byte[] readValue() throws IOException {
-        JavaClass cl = getClazz();
-        int idSize = cl.getIdentifierSize();
-        ReadBuffer buf = cl.getReadBuffer();
-        long offset = getOffset() + 2*idSize + 4;
-        int length = buf.getInt(offset);
-        if (length == 0) {
-            return Snapshot.EMPTY_BYTE_ARRAY;
-        } else {
-            byte[] res = new byte[length];
-            buf.get(offset + 4, res);
-            return res;
-        }
-    }
-
-    private JavaThing[] parseFields(byte[] data, boolean verbose) {
-        JavaClass cl = getClazz();
-        int target = cl.getNumFieldsForInstance();
-        JavaField[] fields = cl.getFields();
-        JavaThing[] fieldValues = new JavaThing[target];
-        Snapshot snapshot = cl.getSnapshot();
-        int idSize = snapshot.getIdentifierSize();
-        int fieldNo = 0;
-        // In the dump file, the fields are stored in this order:
-        // fields of most derived class (immediate class) are stored
-        // first and then the super class and so on. In this object,
-        // fields are stored in the reverse ("natural") order. i.e.,
-        // fields of most super class are stored first.
-
-        // target variable is used to compensate for the fact that
-        // the dump file starts field values from the leaf working
-        // upwards in the inheritance hierarchy, whereas JavaObject
-        // starts with the top of the inheritance hierarchy and works down.
-        target -= fields.length;
-        JavaClass currClass = cl;
-        int index = 0;
-        for (int i = 0; i < fieldValues.length; i++, fieldNo++) {
-            while (fieldNo >= fields.length) {
-                currClass = currClass.getSuperclass();
-                fields = currClass.getFields();
-                fieldNo = 0;
-                target -= fields.length;
-            }
-            JavaField f = fields[fieldNo];
-            char sig = f.getSignature().charAt(0);
-            switch (sig) {
-                case 'L':
-                case '[': {
-                    long id = objectIdAt(index, data);
-                    index += idSize;
-                    JavaObjectRef ref = new JavaObjectRef(id);
-                    fieldValues[target+fieldNo] = ref.dereference(snapshot, f, verbose);
-                    break;
-                }
-                case 'Z': {
-                    byte value = byteAt(index, data);
-                    index++;
-                    fieldValues[target+fieldNo] = new JavaBoolean(value != 0);
-                    break;
-                }
-                case 'B': {
-                    byte value = byteAt(index, data);
-                    index++;
-                    fieldValues[target+fieldNo] = new JavaByte(value);
-                    break;
-                }
-                case 'S': {
-                    short value = shortAt(index, data);
-                    index += 2;
-                    fieldValues[target+fieldNo] = new JavaShort(value);
-                    break;
-                }
-                case 'C': {
-                    char value = charAt(index, data);
-                    index += 2;
-                    fieldValues[target+fieldNo] = new JavaChar(value);
-                    break;
-                }
-                case 'I': {
-                    int value = intAt(index, data);
-                    index += 4;
-                    fieldValues[target+fieldNo] = new JavaInt(value);
-                    break;
-                }
-                case 'J': {
-                    long value = longAt(index, data);
-                    index += 8;
-                    fieldValues[target+fieldNo] = new JavaLong(value);
-                    break;
-                }
-                case 'F': {
-                    float value = floatAt(index, data);
-                    index += 4;
-                    fieldValues[target+fieldNo] = new JavaFloat(value);
-                    break;
-                }
-                case 'D': {
-                    double value = doubleAt(index, data);
-                    index += 8;
-                    fieldValues[target+fieldNo] = new JavaDouble(value);
-                    break;
-                }
-                default:
-                    throw new RuntimeException("invalid signature: " + sig);
-            }
-        }
-        return fieldValues;
-    }
-
-    private void warn(String msg) {
-        System.out.println("WARNING: " + msg);
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaObjectArray.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,172 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-import java.io.IOException;
-import com.sun.tools.hat.internal.parser.ReadBuffer;
-
-/**
- * @author      Bill Foote
- */
-public class JavaObjectArray extends JavaLazyReadObject {
-
-    private Object clazz;  // Long before resolve, the class after resolve
-
-    public JavaObjectArray(long classID, long offset) {
-        super(offset);
-        this.clazz = makeId(classID);
-    }
-
-    public JavaClass getClazz() {
-        return (JavaClass) clazz;
-    }
-
-    public void resolve(Snapshot snapshot) {
-        if (clazz instanceof JavaClass) {
-            return;
-        }
-        long classID = getIdValue((Number)clazz);
-        if (snapshot.isNewStyleArrayClass()) {
-            // Modern heap dumps do this
-            JavaThing t = snapshot.findThing(classID);
-            if (t instanceof JavaClass) {
-                clazz = (JavaClass) t;
-            }
-        }
-        if (!(clazz instanceof JavaClass)) {
-            JavaThing t = snapshot.findThing(classID);
-            if (t != null && t instanceof JavaClass) {
-                JavaClass el = (JavaClass) t;
-                String nm = el.getName();
-                if (!nm.startsWith("[")) {
-                    nm = "L" + el.getName() + ";";
-                }
-                clazz = snapshot.getArrayClass(nm);
-            }
-        }
-
-        if (!(clazz instanceof JavaClass)) {
-            clazz = snapshot.getOtherArrayType();
-        }
-        ((JavaClass)clazz).addInstance(this);
-        super.resolve(snapshot);
-    }
-
-    public JavaThing[] getValues() {
-        return getElements();
-    }
-
-    public JavaThing[] getElements() {
-        Snapshot snapshot = getClazz().getSnapshot();
-        byte[] data = getValue();
-        final int idSize = snapshot.getIdentifierSize();
-        final int numElements = data.length / idSize;
-        JavaThing[] elements = new JavaThing[numElements];
-        int index = 0;
-        for (int i = 0; i < elements.length; i++) {
-            long id = objectIdAt(index, data);
-            index += idSize;
-            elements[i] = snapshot.findThing(id);
-        }
-        return elements;
-    }
-
-    public int compareTo(JavaThing other) {
-        if (other instanceof JavaObjectArray) {
-            return 0;
-        }
-        return super.compareTo(other);
-    }
-
-    public int getLength() {
-        return getValueLength() / getClazz().getIdentifierSize();
-    }
-
-    public void visitReferencedObjects(JavaHeapObjectVisitor v) {
-        super.visitReferencedObjects(v);
-        JavaThing[] elements = getElements();
-        for (int i = 0; i < elements.length; i++) {
-            if (elements[i] != null && elements[i] instanceof JavaHeapObject) {
-                v.visit((JavaHeapObject) elements[i]);
-            }
-        }
-    }
-
-    /**
-     * Describe the reference that this thing has to target.  This will only
-     * be called if target is in the array returned by getChildrenForRootset.
-     */
-    public String describeReferenceTo(JavaThing target, Snapshot ss) {
-        JavaThing[] elements = getElements();
-        for (int i = 0; i < elements.length; i++) {
-            if (elements[i] == target) {
-                return "Element " + i + " of " + this;
-            }
-        }
-        return super.describeReferenceTo(target, ss);
-    }
-
-    /*
-     * Java object array record (HPROF_GC_OBJ_ARRAY_DUMP)
-     * looks as below:
-     *
-     *     object ID
-     *     stack trace serial number (int)
-     *     array length (int)
-     *     array class ID
-     *     array element IDs
-     */
-    protected final int readValueLength() throws IOException {
-        JavaClass cl = getClazz();
-        ReadBuffer buf = cl.getReadBuffer();
-        int idSize = cl.getIdentifierSize();
-        long offset = getOffset() + idSize + 4;
-        int len = buf.getInt(offset);
-        return len * cl.getIdentifierSize();
-    }
-
-    protected final byte[] readValue() throws IOException {
-        JavaClass cl = getClazz();
-        ReadBuffer buf = cl.getReadBuffer();
-        int idSize = cl.getIdentifierSize();
-        long offset = getOffset() + idSize + 4;
-        int len = buf.getInt(offset);
-        if (len == 0) {
-            return Snapshot.EMPTY_BYTE_ARRAY;
-        } else {
-            byte[] res = new byte[len * idSize];
-            buf.get(offset + 4 + idSize, res);
-            return res;
-        }
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaObjectRef.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,97 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-import com.sun.tools.hat.internal.util.Misc;
-
-/**
- * A forward reference to an object.  This is an intermediate representation
- * for a JavaThing, when we have the thing's ID, but we might not have read
- * the thing yet.
- *
- * @author      Bill Foote
- */
-public class JavaObjectRef extends JavaThing {
-    private long id;
-
-    public JavaObjectRef(long id) {
-        this.id = id;
-    }
-
-    public long getId() {
-        return id;
-    }
-
-    public boolean isHeapAllocated() {
-        return true;
-    }
-
-    public JavaThing dereference(Snapshot snapshot, JavaField field) {
-        return dereference(snapshot, field, true);
-    }
-
-    public JavaThing dereference(Snapshot snapshot, JavaField field, boolean verbose) {
-        if (field != null && !field.hasId()) {
-            // If this happens, we must be a field that represents an int.
-            // (This only happens with .bod-style files)
-            return new JavaLong(id);
-        }
-        if (id == 0) {
-            return snapshot.getNullThing();
-        }
-        JavaThing result = snapshot.findThing(id);
-        if (result == null) {
-            if (!snapshot.getUnresolvedObjectsOK() && verbose) {
-                String msg = "WARNING:  Failed to resolve object id "
-                                + Misc.toHex(id);
-                if (field != null) {
-                    msg += " for field " + field.getName()
-                            + " (signature " + field.getSignature() + ")";
-                }
-                System.out.println(msg);
-                // Thread.dumpStack();
-            }
-            result = new HackJavaValue("Unresolved object "
-                                        + Misc.toHex(id), 0);
-        }
-        return result;
-    }
-
-    public int getSize() {
-        return 0;
-    }
-
-    public String toString() {
-        return "Unresolved object " + Misc.toHex(id);
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaShort.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,54 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-/**
- * Represents a short (i.e. a short field in an instance).
- *
- * @author      Bill Foote
- */
-
-
-public class JavaShort extends JavaValue {
-
-    short value;
-
-    public JavaShort(short value) {
-        this.value = value;
-    }
-
-    public String toString() {
-        return "" + value;
-    }
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaStatic.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,79 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-/**
- *
- * @author      Bill Foote
- */
-
-/**
- * Represents the value of a static field of a JavaClass
- */
-
-public class JavaStatic {
-
-    private JavaField field;
-    private JavaThing value;
-
-    public JavaStatic(JavaField field, JavaThing value) {
-        this.field = field;
-        this.value = value;
-    }
-
-    public void resolve(JavaClass clazz, Snapshot snapshot) {
-        long id = -1;
-        if (value instanceof JavaObjectRef) {
-            id = ((JavaObjectRef)value).getId();
-        }
-        value = value.dereference(snapshot, field);
-        if (value.isHeapAllocated() &&
-            clazz.getLoader() == snapshot.getNullThing()) {
-            // static fields are only roots if they are in classes
-            //    loaded by the root classloader.
-            JavaHeapObject ho = (JavaHeapObject) value;
-            String s = "Static reference from " + clazz.getName()
-                       + "." + field.getName();
-            snapshot.addRoot(new Root(id, clazz.getId(),
-                                      Root.JAVA_STATIC, s));
-        }
-    }
-
-    public JavaField getField() {
-        return field;
-    }
-
-    public JavaThing getValue() {
-        return value;
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaThing.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,99 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-import java.util.Enumeration;
-import java.util.Hashtable;
-
-
-/**
- *
- * @author      Bill Foote
- */
-
-
-/**
- * Represents a java "Thing".  A thing is anything that can be the value of
- * a field.  This includes JavaHeapObject, JavaObjectRef, and JavaValue.
- */
-
-public abstract class JavaThing {
-
-    protected JavaThing() {
-    }
-
-    /**
-     * If this is a forward reference, figure out what it really
-     * refers to.
-     *
-     * @param snapshot  The snapshot this is for
-     * @param field     The field this thing represents.  If null, it is
-     *                  assumed this thing is an object (and never a value).
-     */
-    public JavaThing dereference(Snapshot shapshot, JavaField field) {
-        return this;
-    }
-
-
-    /**
-     * Are we the same type as other?
-     *
-     * @see JavaObject.isSameTypeAs()
-     */
-    public boolean isSameTypeAs(JavaThing other) {
-        return getClass() == other.getClass();
-    }
-    /**
-     * @return true iff this represents a heap-allocated object
-     */
-    abstract public boolean isHeapAllocated();
-
-    /**
-     * @return the size of this object, in bytes, including VM overhead
-     */
-    abstract public int getSize();
-
-    /**
-     * @return a human-readable string representation of this thing
-     */
-    abstract public String toString();
-
-    /**
-     * Compare our string representation to other's
-     * @see java.lang.String.compareTo()
-     */
-    public int compareTo(JavaThing other) {
-        return toString().compareTo(other.toString());
-    }
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaValue.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,61 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-/**
- * Abstract base class for all value types (ints, longs, floats, etc.)
- *
- * @author      Bill Foote
- */
-
-
-
-
-public abstract class JavaValue extends JavaThing {
-
-    protected JavaValue() {
-    }
-
-    public boolean isHeapAllocated() {
-        return false;
-    }
-
-    abstract public String toString();
-
-    public int getSize() {
-        // The size of a value is already accounted for in the class
-        // that has the data member.
-        return 0;
-    }
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/JavaValueArray.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,433 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-import com.sun.tools.hat.internal.parser.ReadBuffer;
-import java.io.IOException;
-
-/**
- * An array of values, that is, an array of ints, boolean, floats or the like.
- *
- * @author      Bill Foote
- */
-public class JavaValueArray extends JavaLazyReadObject
-                /*imports*/ implements ArrayTypeCodes {
-
-    private static String arrayTypeName(byte sig) {
-        switch (sig) {
-            case 'B':
-                return "byte[]";
-            case 'Z':
-                return "boolean[]";
-            case 'C':
-                return "char[]";
-            case 'S':
-                return "short[]";
-            case 'I':
-                return "int[]";
-            case 'F':
-                return "float[]";
-            case 'J':
-                return "long[]";
-            case 'D':
-                return "double[]";
-            default:
-                throw new RuntimeException("invalid array element sig: " + sig);
-        }
-    }
-
-    private static int elementSize(byte type) {
-        switch (type) {
-            case T_BYTE:
-            case T_BOOLEAN:
-                return 1;
-            case T_CHAR:
-            case T_SHORT:
-                return 2;
-            case T_INT:
-            case T_FLOAT:
-                return 4;
-            case T_LONG:
-            case T_DOUBLE:
-                return 8;
-            default:
-                throw new RuntimeException("invalid array element type: " + type);
-        }
-    }
-
-    /*
-     * Java primitive array record (HPROF_GC_PRIM_ARRAY_DUMP) looks
-     * as below:
-     *
-     *    object ID
-     *    stack trace serial number (int)
-     *    length of the instance data (int)
-     *    element type (byte)
-     *    array data
-     */
-    protected final int readValueLength() throws IOException {
-        JavaClass cl = getClazz();
-        ReadBuffer buf = cl.getReadBuffer();
-        int idSize = cl.getIdentifierSize();
-        long offset = getOffset() + idSize + 4;
-        // length of the array
-        int len = buf.getInt(offset);
-        // typecode of array element type
-        byte type = buf.getByte(offset + 4);
-        return len * elementSize(type);
-    }
-
-    protected final byte[] readValue() throws IOException {
-        JavaClass cl = getClazz();
-        ReadBuffer buf = cl.getReadBuffer();
-        int idSize = cl.getIdentifierSize();
-        long offset = getOffset() + idSize + 4;
-        // length of the array
-        int length = buf.getInt(offset);
-        // typecode of array element type
-        byte type = buf.getByte(offset + 4);
-        if (length == 0) {
-            return Snapshot.EMPTY_BYTE_ARRAY;
-        } else {
-            length *= elementSize(type);
-            byte[] res = new byte[length];
-            buf.get(offset + 5, res);
-            return res;
-        }
-    }
-
-    // JavaClass set only after resolve.
-    private JavaClass clazz;
-
-    // This field contains elementSignature byte and
-    // divider to be used to calculate length. Note that
-    // length of content byte[] is not same as array length.
-    // Actual array length is (byte[].length / divider)
-    private int data;
-
-    // First 8 bits of data is used for element signature
-    private static final int SIGNATURE_MASK = 0x0FF;
-
-    // Next 8 bits of data is used for length divider
-    private static final int LENGTH_DIVIDER_MASK = 0x0FF00;
-
-    // Number of bits to shift to get length divider
-    private static final int LENGTH_DIVIDER_SHIFT = 8;
-
-    public JavaValueArray(byte elementSignature, long offset) {
-        super(offset);
-        this.data = (elementSignature & SIGNATURE_MASK);
-    }
-
-    public JavaClass getClazz() {
-        return clazz;
-    }
-
-    public void visitReferencedObjects(JavaHeapObjectVisitor v) {
-        super.visitReferencedObjects(v);
-    }
-
-    public void resolve(Snapshot snapshot) {
-        if (clazz instanceof JavaClass) {
-            return;
-        }
-        byte elementSig = getElementType();
-        clazz = snapshot.findClass(arrayTypeName(elementSig));
-        if (clazz == null) {
-            clazz = snapshot.getArrayClass("" + ((char) elementSig));
-        }
-        getClazz().addInstance(this);
-        super.resolve(snapshot);
-    }
-
-    public int getLength() {
-        int divider = (data & LENGTH_DIVIDER_MASK) >>> LENGTH_DIVIDER_SHIFT;
-        if (divider == 0) {
-            byte elementSignature = getElementType();
-            switch (elementSignature) {
-            case 'B':
-            case 'Z':
-                divider = 1;
-                break;
-            case 'C':
-            case 'S':
-                divider = 2;
-                break;
-            case 'I':
-            case 'F':
-                divider = 4;
-                break;
-            case 'J':
-            case 'D':
-                divider = 8;
-                break;
-            default:
-                throw new RuntimeException("unknown primitive type: " +
-                                elementSignature);
-            }
-            data |= (divider << LENGTH_DIVIDER_SHIFT);
-        }
-        return (getValueLength() / divider);
-    }
-
-    public Object getElements() {
-        final int len = getLength();
-        final byte et = getElementType();
-        byte[] data = getValue();
-        int index = 0;
-        switch (et) {
-            case 'Z': {
-                boolean[] res = new boolean[len];
-                for (int i = 0; i < len; i++) {
-                    res[i] = booleanAt(index, data);
-                    index++;
-                }
-                return res;
-            }
-            case 'B': {
-                byte[] res = new byte[len];
-                for (int i = 0; i < len; i++) {
-                    res[i] = byteAt(index, data);
-                    index++;
-                }
-                return res;
-            }
-            case 'C': {
-                char[] res = new char[len];
-                for (int i = 0; i < len; i++) {
-                    res[i] = charAt(index, data);
-                    index += 2;
-                }
-                return res;
-            }
-            case 'S': {
-                short[] res = new short[len];
-                for (int i = 0; i < len; i++) {
-                    res[i] = shortAt(index, data);
-                    index += 2;
-                }
-                return res;
-            }
-            case 'I': {
-                int[] res = new int[len];
-                for (int i = 0; i < len; i++) {
-                    res[i] = intAt(index, data);
-                    index += 4;
-                }
-                return res;
-            }
-            case 'J': {
-                long[] res = new long[len];
-                for (int i = 0; i < len; i++) {
-                    res[i] = longAt(index, data);
-                    index += 8;
-                }
-                return res;
-            }
-            case 'F': {
-                float[] res = new float[len];
-                for (int i = 0; i < len; i++) {
-                    res[i] = floatAt(index, data);
-                    index += 4;
-                }
-                return res;
-            }
-            case 'D': {
-                double[] res = new double[len];
-                for (int i = 0; i < len; i++) {
-                    res[i] = doubleAt(index, data);
-                    index += 8;
-                }
-                return res;
-            }
-            default: {
-                throw new RuntimeException("unknown primitive type?");
-            }
-        }
-    }
-
-    public byte getElementType() {
-        return (byte) (data & SIGNATURE_MASK);
-    }
-
-    private void checkIndex(int index) {
-        if (index < 0 || index >= getLength()) {
-            throw new ArrayIndexOutOfBoundsException(index);
-        }
-    }
-
-    private void requireType(char type) {
-        if (getElementType() != type) {
-            throw new RuntimeException("not of type : " + type);
-        }
-    }
-
-    public boolean getBooleanAt(int index) {
-        checkIndex(index);
-        requireType('Z');
-        return booleanAt(index, getValue());
-    }
-
-    public byte getByteAt(int index) {
-        checkIndex(index);
-        requireType('B');
-        return byteAt(index, getValue());
-    }
-
-    public char getCharAt(int index) {
-        checkIndex(index);
-        requireType('C');
-        return charAt(index << 1, getValue());
-    }
-
-    public short getShortAt(int index) {
-        checkIndex(index);
-        requireType('S');
-        return shortAt(index << 1, getValue());
-    }
-
-    public int getIntAt(int index) {
-        checkIndex(index);
-        requireType('I');
-        return intAt(index << 2, getValue());
-    }
-
-    public long getLongAt(int index) {
-        checkIndex(index);
-        requireType('J');
-        return longAt(index << 3, getValue());
-    }
-
-    public float getFloatAt(int index) {
-        checkIndex(index);
-        requireType('F');
-        return floatAt(index << 2, getValue());
-    }
-
-    public double getDoubleAt(int index) {
-        checkIndex(index);
-        requireType('D');
-        return doubleAt(index << 3, getValue());
-    }
-
-    public String valueString() {
-        return valueString(true);
-    }
-
-    public String valueString(boolean bigLimit) {
-        // Char arrays deserve special treatment
-        StringBuilder result;
-        byte[] value = getValue();
-        int max = value.length;
-        byte elementSignature = getElementType();
-        if (elementSignature == 'C')  {
-            result = new StringBuilder();
-            for (int i = 0; i < value.length; ) {
-                char val = charAt(i, value);
-                result.append(val);
-                i += 2;
-            }
-        } else {
-            int limit = 8;
-            if (bigLimit) {
-                limit = 1000;
-            }
-            result = new StringBuilder("{");
-            int num = 0;
-            for (int i = 0; i < value.length; ) {
-                if (num > 0) {
-                    result.append(", ");
-                }
-                if (num >= limit) {
-                    result.append("... ");
-                    break;
-                }
-                num++;
-                switch (elementSignature) {
-                    case 'Z': {
-                        boolean val = booleanAt(i, value);
-                        if (val) {
-                            result.append("true");
-                        } else {
-                            result.append("false");
-                        }
-                        i++;
-                        break;
-                    }
-                    case 'B': {
-                        int val = 0xFF & byteAt(i, value);
-                        result.append("0x").append(Integer.toString(val, 16));
-                        i++;
-                        break;
-                    }
-                    case 'S': {
-                        short val = shortAt(i, value);
-                        i += 2;
-                        result.append(val);
-                        break;
-                    }
-                    case 'I': {
-                        int val = intAt(i, value);
-                        i += 4;
-                        result.append(val);
-                        break;
-                    }
-                    case 'J': {         // long
-                        long val = longAt(i, value);
-                        result.append(val);
-                        i += 8;
-                        break;
-                    }
-                    case 'F': {
-                        float val = floatAt(i, value);
-                        result.append(val);
-                        i += 4;
-                        break;
-                    }
-                    case 'D': {         // double
-                        double val = doubleAt(i, value);
-                        result.append(val);
-                        i += 8;
-                        break;
-                    }
-                    default: {
-                        throw new RuntimeException("unknown primitive type?");
-                    }
-                }
-            }
-            result.append('}');
-        }
-        return result.toString();
-    }
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/ReachableExcludes.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,50 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-
-/**
- * This represents a set of data members that should be excluded from the
- * reachable objects query. This is useful to exclude observers from the
- * transitive closure of objects reachable from a given object, allowing
- * some kind of real determination of the "size" of that object.
- *
- */
-
-public interface ReachableExcludes {
-    /**
-     * @return true iff the given field is on the hitlist of excluded
-     *          fields.
-     */
-    public boolean isExcluded(String fieldName);
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/ReachableExcludesImpl.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,105 +0,0 @@
-/*
- * Copyright (c) 1997, 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-import java.io.File;
-import java.io.FileInputStream;
-import java.io.InputStreamReader;
-import java.io.Reader;
-import java.io.BufferedReader;
-import java.io.IOException;
-
-import java.util.Hashtable;
-
-/**
- * This represents a set of data members that should be excluded from the
- * reachable objects query.
- * This is useful to exclude observers from the
- * transitive closure of objects reachable from a given object, allowing
- * some kind of real determination of the "size" of that object.
- *
- * @author      Bill Foote
- */
-public class ReachableExcludesImpl implements ReachableExcludes {
-
-    private File excludesFile;
-    private long lastModified;
-    private Hashtable<String, String> methods;  // Used as a bag
-
-    /**
-     * Create a new ReachableExcludesImpl over the given file.  The file will be
-     * re-read whenever the timestamp changes.
-     */
-    public ReachableExcludesImpl(File excludesFile) {
-        this.excludesFile = excludesFile;
-        readFile();
-    }
-
-    private void readFileIfNeeded() {
-        if (excludesFile.lastModified() != lastModified) {
-            synchronized(this) {
-                if (excludesFile.lastModified() != lastModified) {
-                    readFile();
-                }
-            }
-        }
-    }
-
-    private void readFile() {
-        long lm = excludesFile.lastModified();
-        Hashtable<String, String> m = new Hashtable<String, String>();
-
-        try {
-            BufferedReader r = new BufferedReader(new InputStreamReader(
-                                    new FileInputStream(excludesFile)));
-
-            String method;
-            while ((method = r.readLine()) != null) {
-                m.put(method, method);
-            }
-            lastModified = lm;
-            methods = m;        // We want this to be atomic
-        } catch (IOException ex) {
-            System.out.println("Error reading " + excludesFile + ":  " + ex);
-        }
-    }
-
-    /**
-     * @return true iff the given field is on the histlist of excluded
-     *          fields.
-     */
-    public boolean isExcluded(String fieldName) {
-        readFileIfNeeded();
-        return methods.get(fieldName) != null;
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/ReachableObjects.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,148 +0,0 @@
-/*
- * Copyright (c) 1997, 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-import java.util.Vector;
-import java.util.Hashtable;
-import java.util.Enumeration;
-
-import com.sun.tools.hat.internal.util.ArraySorter;
-import com.sun.tools.hat.internal.util.Comparer;
-
-/**
- * @author      A. Sundararajan
- */
-
-public class ReachableObjects {
-    public ReachableObjects(JavaHeapObject root,
-                            final ReachableExcludes excludes) {
-        this.root = root;
-
-        final Hashtable<JavaHeapObject, JavaHeapObject> bag = new Hashtable<JavaHeapObject, JavaHeapObject>();
-        final Hashtable<String, String> fieldsExcluded = new Hashtable<String, String>();  //Bag<String>
-        final Hashtable<String, String> fieldsUsed = new Hashtable<String, String>();   // Bag<String>
-        JavaHeapObjectVisitor visitor = new AbstractJavaHeapObjectVisitor() {
-            public void visit(JavaHeapObject t) {
-                // Size is zero for things like integer fields
-                if (t != null && t.getSize() > 0 && bag.get(t) == null) {
-                    bag.put(t, t);
-                    t.visitReferencedObjects(this);
-                }
-            }
-
-            public boolean mightExclude() {
-                return excludes != null;
-            }
-
-            public boolean exclude(JavaClass clazz, JavaField f) {
-                if (excludes == null) {
-                    return false;
-                }
-                String nm = clazz.getName() + "." + f.getName();
-                if (excludes.isExcluded(nm)) {
-                    fieldsExcluded.put(nm, nm);
-                    return true;
-                } else {
-                    fieldsUsed.put(nm, nm);
-                    return false;
-                }
-            }
-        };
-        // Put the closure of root and all objects reachable from root into
-        // bag (depth first), but don't include root:
-        visitor.visit(root);
-        bag.remove(root);
-
-        // Now grab the elements into a vector, and sort it in decreasing size
-        JavaThing[] things = new JavaThing[bag.size()];
-        int i = 0;
-        for (Enumeration<JavaHeapObject> e = bag.elements(); e.hasMoreElements(); ) {
-            things[i++] = (JavaThing) e.nextElement();
-        }
-        ArraySorter.sort(things, new Comparer() {
-            public int compare(Object lhs, Object rhs) {
-                JavaThing left = (JavaThing) lhs;
-                JavaThing right = (JavaThing) rhs;
-                int diff = right.getSize() - left.getSize();
-                if (diff != 0) {
-                    return diff;
-                }
-                return left.compareTo(right);
-            }
-        });
-        this.reachables = things;
-
-        this.totalSize = root.getSize();
-        for (i = 0; i < things.length; i++) {
-            this.totalSize += things[i].getSize();
-        }
-
-        excludedFields = getElements(fieldsExcluded);
-        usedFields = getElements(fieldsUsed);
-    }
-
-    public JavaHeapObject getRoot() {
-        return root;
-    }
-
-    public JavaThing[] getReachables() {
-        return reachables;
-    }
-
-    public long getTotalSize() {
-        return totalSize;
-    }
-
-    public String[] getExcludedFields() {
-        return excludedFields;
-    }
-
-    public String[] getUsedFields() {
-        return usedFields;
-    }
-
-    private String[] getElements(Hashtable<?, ?> ht) {
-        Object[] keys = ht.keySet().toArray();
-        int len = keys.length;
-        String[] res = new String[len];
-        System.arraycopy(keys, 0, res, 0, len);
-        ArraySorter.sortArrayOfStrings(res);
-        return res;
-    }
-
-    private JavaHeapObject root;
-    private JavaThing[] reachables;
-    private String[]  excludedFields;
-    private String[]  usedFields;
-    private long totalSize;
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/ReferenceChain.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,69 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-/**
- * Represents a chain of references to some target object
- *
- * @author      Bill Foote
- */
-
-public class ReferenceChain {
-
-    JavaHeapObject      obj;    // Object referred to
-    ReferenceChain      next;   // Next in chain
-
-    public ReferenceChain(JavaHeapObject obj, ReferenceChain next) {
-        this.obj = obj;
-        this.next = next;
-    }
-
-    public JavaHeapObject getObj() {
-        return obj;
-    }
-
-    public ReferenceChain getNext() {
-        return next;
-    }
-
-    public int getDepth() {
-        int count = 1;
-        ReferenceChain tmp = next;
-        while (tmp != null) {
-            count++;
-            tmp = tmp.next;
-        }
-        return count;
-    }
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/Root.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,174 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-import com.sun.tools.hat.internal.util.Misc;
-
-/**
- *
- * @author      Bill Foote
- */
-
-
-/**
- * Represents a member of the rootset, that is, one of the objects that
- * the GC starts from when marking reachable objects.
- */
-
-public class Root {
-
-    private long id;            // ID of the JavaThing we refer to
-    private long refererId;     // Thread or Class responsible for this, or 0
-    private int index = -1;             // Index in Snapshot.roots
-    private int type;
-    private String description;
-    private JavaHeapObject referer = null;
-    private StackTrace stackTrace = null;
-
-    // Values for type.  Higher values are more interesting -- see getType().
-    // See also getTypeName()
-    public final static int INVALID_TYPE = 0;
-    public final static int UNKNOWN = 1;
-    public final static int SYSTEM_CLASS = 2;
-
-    public final static int NATIVE_LOCAL = 3;
-    public final static int NATIVE_STATIC = 4;
-    public final static int THREAD_BLOCK = 5;
-    public final static int BUSY_MONITOR = 6;
-    public final static int JAVA_LOCAL = 7;
-    public final static int NATIVE_STACK = 8;
-    public final static int JAVA_STATIC = 9;
-
-
-    public Root(long id, long refererId, int type, String description) {
-        this(id, refererId, type, description, null);
-    }
-
-
-    public Root(long id, long refererId, int type, String description,
-                StackTrace stackTrace) {
-        this.id = id;
-        this.refererId = refererId;
-        this.type = type;
-        this.description = description;
-        this.stackTrace = stackTrace;
-    }
-
-    public long getId() {
-        return id;
-    }
-
-    public String getIdString() {
-        return Misc.toHex(id);
-    }
-
-    public String getDescription() {
-        if ("".equals(description)) {
-            return getTypeName() + " Reference";
-        } else {
-            return description;
-        }
-    }
-
-    /**
-     * Return type.  We guarantee that more interesting roots will have
-     * a type that is numerically higher.
-     */
-    public int getType() {
-        return type;
-    }
-
-    public String getTypeName() {
-        switch(type) {
-            case INVALID_TYPE:          return "Invalid (?!?)";
-            case UNKNOWN:               return "Unknown";
-            case SYSTEM_CLASS:          return "System Class";
-            case NATIVE_LOCAL:          return "JNI Local";
-            case NATIVE_STATIC:         return "JNI Global";
-            case THREAD_BLOCK:          return "Thread Block";
-            case BUSY_MONITOR:          return "Busy Monitor";
-            case JAVA_LOCAL:            return "Java Local";
-            case NATIVE_STACK:          return "Native Stack (possibly Java local)";
-            case JAVA_STATIC:           return "Java Static";
-            default:                    return "??";
-        }
-    }
-
-    /**
-     * Given two Root instances, return the one that is most interesting.
-     */
-    public Root mostInteresting(Root other) {
-        if (other.type > this.type) {
-            return other;
-        } else {
-            return this;
-        }
-    }
-
-    /**
-     * Get the object that's responsible for this root, if there is one.
-     * This will be null, a Thread object, or a Class object.
-     */
-    public JavaHeapObject getReferer() {
-        return referer;
-    }
-
-    /**
-     * @return the stack trace responsible for this root, or null if there
-     * is none.
-     */
-    public StackTrace getStackTrace() {
-        return stackTrace;
-    }
-
-    /**
-     * @return The index of this root in Snapshot.roots
-     */
-    public int getIndex() {
-        return index;
-    }
-
-    void resolve(Snapshot ss) {
-        if (refererId != 0) {
-            referer = ss.findThing(refererId);
-        }
-        if (stackTrace != null) {
-            stackTrace.resolve(ss);
-        }
-    }
-
-    void setIndex(int i) {
-        index = i;
-    }
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/Snapshot.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,630 +0,0 @@
-/*
- * Copyright (c) 1997, 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-import java.lang.ref.SoftReference;
-import java.util.*;
-import com.sun.tools.hat.internal.parser.ReadBuffer;
-import com.sun.tools.hat.internal.util.Misc;
-
-/**
- *
- * @author      Bill Foote
- */
-
-/**
- * Represents a snapshot of the Java objects in the VM at one instant.
- * This is the top-level "model" object read out of a single .hprof or .bod
- * file.
- */
-
-public class Snapshot {
-
-    public static long SMALL_ID_MASK = 0x0FFFFFFFFL;
-    public static final byte[] EMPTY_BYTE_ARRAY = new byte[0];
-
-    private static final JavaField[] EMPTY_FIELD_ARRAY = new JavaField[0];
-    private static final JavaStatic[] EMPTY_STATIC_ARRAY = new JavaStatic[0];
-
-    // all heap objects
-    private Hashtable<Number, JavaHeapObject> heapObjects =
-                 new Hashtable<Number, JavaHeapObject>();
-
-    private Hashtable<Number, JavaClass> fakeClasses =
-                 new Hashtable<Number, JavaClass>();
-
-    // all Roots in this Snapshot
-    private Vector<Root> roots = new Vector<Root>();
-
-    // name-to-class map
-    private Map<String, JavaClass> classes =
-                 new TreeMap<String, JavaClass>();
-
-    // new objects relative to a baseline - lazily initialized
-    private volatile Map<JavaHeapObject, Boolean> newObjects;
-
-    // allocation site traces for all objects - lazily initialized
-    private volatile Map<JavaHeapObject, StackTrace> siteTraces;
-
-    // object-to-Root map for all objects
-    private Map<JavaHeapObject, Root> rootsMap =
-                 new HashMap<JavaHeapObject, Root>();
-
-    // soft cache of finalizeable objects - lazily initialized
-    private SoftReference<Vector<?>> finalizablesCache;
-
-    // represents null reference
-    private JavaThing nullThing;
-
-    // java.lang.ref.Reference class
-    private JavaClass weakReferenceClass;
-    // index of 'referent' field in java.lang.ref.Reference class
-    private int referentFieldIndex;
-
-    // java.lang.Class class
-    private JavaClass javaLangClass;
-    // java.lang.String class
-    private JavaClass javaLangString;
-    // java.lang.ClassLoader class
-    private JavaClass javaLangClassLoader;
-
-    // unknown "other" array class
-    private volatile JavaClass otherArrayType;
-    // Stuff to exclude from reachable query
-    private ReachableExcludes reachableExcludes;
-    // the underlying heap dump buffer
-    private ReadBuffer readBuf;
-
-    // True iff some heap objects have isNew set
-    private boolean hasNewSet;
-    private boolean unresolvedObjectsOK;
-
-    // whether object array instances have new style class or
-    // old style (element) class.
-    private boolean newStyleArrayClass;
-
-    // object id size in the heap dump
-    private int identifierSize = 4;
-
-    // minimum object size - accounts for object header in
-    // most Java virtual machines - we assume 2 identifierSize
-    // (which is true for Sun's hotspot JVM).
-    private int minimumObjectSize;
-
-    public Snapshot(ReadBuffer buf) {
-        nullThing = new HackJavaValue("<null>", 0);
-        readBuf = buf;
-    }
-
-    public void setSiteTrace(JavaHeapObject obj, StackTrace trace) {
-        if (trace != null && trace.getFrames().length != 0) {
-            initSiteTraces();
-            siteTraces.put(obj, trace);
-        }
-    }
-
-    public StackTrace getSiteTrace(JavaHeapObject obj) {
-        if (siteTraces != null) {
-            return siteTraces.get(obj);
-        } else {
-            return null;
-        }
-    }
-
-    public void setNewStyleArrayClass(boolean value) {
-        newStyleArrayClass = value;
-    }
-
-    public boolean isNewStyleArrayClass() {
-        return newStyleArrayClass;
-    }
-
-    public void setIdentifierSize(int size) {
-        identifierSize = size;
-        minimumObjectSize = 2 * size;
-    }
-
-    public int getIdentifierSize() {
-        return identifierSize;
-    }
-
-    public int getMinimumObjectSize() {
-        return minimumObjectSize;
-    }
-
-    public void addHeapObject(long id, JavaHeapObject ho) {
-        heapObjects.put(makeId(id), ho);
-    }
-
-    public void addRoot(Root r) {
-        r.setIndex(roots.size());
-        roots.addElement(r);
-    }
-
-    public void addClass(long id, JavaClass c) {
-        addHeapObject(id, c);
-        putInClassesMap(c);
-    }
-
-    JavaClass addFakeInstanceClass(long classID, int instSize) {
-        // Create a fake class name based on ID.
-        String name = "unknown-class<@" + Misc.toHex(classID) + ">";
-
-        // Create fake fields convering the given instance size.
-        // Create as many as int type fields and for the left over
-        // size create byte type fields.
-        int numInts = instSize / 4;
-        int numBytes = instSize % 4;
-        JavaField[] fields = new JavaField[numInts + numBytes];
-        int i;
-        for (i = 0; i < numInts; i++) {
-            fields[i] = new JavaField("unknown-field-" + i, "I");
-        }
-        for (i = 0; i < numBytes; i++) {
-            fields[i + numInts] = new JavaField("unknown-field-" +
-                                                i + numInts, "B");
-        }
-
-        // Create fake instance class
-        JavaClass c = new JavaClass(name, 0, 0, 0, 0, fields,
-                                 EMPTY_STATIC_ARRAY, instSize);
-        // Add the class
-        addFakeClass(makeId(classID), c);
-        return c;
-    }
-
-
-    /**
-     * @return true iff it's possible that some JavaThing instances might
-     *          isNew set
-     *
-     * @see JavaThing.isNew()
-     */
-    public boolean getHasNewSet() {
-        return hasNewSet;
-    }
-
-    //
-    // Used in the body of resolve()
-    //
-    private static class MyVisitor extends AbstractJavaHeapObjectVisitor {
-        JavaHeapObject t;
-        public void visit(JavaHeapObject other) {
-            other.addReferenceFrom(t);
-        }
-    }
-
-    // To show heap parsing progress, we print a '.' after this limit
-    private static final int DOT_LIMIT = 5000;
-
-    /**
-     * Called after reading complete, to initialize the structure
-     */
-    public void resolve(boolean calculateRefs) {
-        System.out.println("Resolving " + heapObjects.size() + " objects...");
-
-        // First, resolve the classes.  All classes must be resolved before
-        // we try any objects, because the objects use classes in their
-        // resolution.
-        javaLangClass = findClass("java.lang.Class");
-        if (javaLangClass == null) {
-            System.out.println("WARNING:  hprof file does not include java.lang.Class!");
-            javaLangClass = new JavaClass("java.lang.Class", 0, 0, 0, 0,
-                                 EMPTY_FIELD_ARRAY, EMPTY_STATIC_ARRAY, 0);
-            addFakeClass(javaLangClass);
-        }
-        javaLangString = findClass("java.lang.String");
-        if (javaLangString == null) {
-            System.out.println("WARNING:  hprof file does not include java.lang.String!");
-            javaLangString = new JavaClass("java.lang.String", 0, 0, 0, 0,
-                                 EMPTY_FIELD_ARRAY, EMPTY_STATIC_ARRAY, 0);
-            addFakeClass(javaLangString);
-        }
-        javaLangClassLoader = findClass("java.lang.ClassLoader");
-        if (javaLangClassLoader == null) {
-            System.out.println("WARNING:  hprof file does not include java.lang.ClassLoader!");
-            javaLangClassLoader = new JavaClass("java.lang.ClassLoader", 0, 0, 0, 0,
-                                 EMPTY_FIELD_ARRAY, EMPTY_STATIC_ARRAY, 0);
-            addFakeClass(javaLangClassLoader);
-        }
-
-        for (JavaHeapObject t : heapObjects.values()) {
-            if (t instanceof JavaClass) {
-                t.resolve(this);
-            }
-        }
-
-        // Now, resolve everything else.
-        for (JavaHeapObject t : heapObjects.values()) {
-            if (!(t instanceof JavaClass)) {
-                t.resolve(this);
-            }
-        }
-
-        heapObjects.putAll(fakeClasses);
-        fakeClasses.clear();
-
-        weakReferenceClass = findClass("java.lang.ref.Reference");
-        if (weakReferenceClass == null)  {      // JDK 1.1.x
-            weakReferenceClass = findClass("sun.misc.Ref");
-            referentFieldIndex = 0;
-        } else {
-            JavaField[] fields = weakReferenceClass.getFieldsForInstance();
-            for (int i = 0; i < fields.length; i++) {
-                if ("referent".equals(fields[i].getName())) {
-                    referentFieldIndex = i;
-                    break;
-                }
-            }
-        }
-
-        if (calculateRefs) {
-            calculateReferencesToObjects();
-            System.out.print("Eliminating duplicate references");
-            System.out.flush();
-            // This println refers to the *next* step
-        }
-        int count = 0;
-        for (JavaHeapObject t : heapObjects.values()) {
-            t.setupReferers();
-            ++count;
-            if (calculateRefs && count % DOT_LIMIT == 0) {
-                System.out.print(".");
-                System.out.flush();
-            }
-        }
-        if (calculateRefs) {
-            System.out.println("");
-        }
-
-        // to ensure that Iterator.remove() on getClasses()
-        // result will throw exception..
-        classes = Collections.unmodifiableMap(classes);
-    }
-
-    private void calculateReferencesToObjects() {
-        System.out.print("Chasing references, expect "
-                         + (heapObjects.size() / DOT_LIMIT) + " dots");
-        System.out.flush();
-        int count = 0;
-        MyVisitor visitor = new MyVisitor();
-        for (JavaHeapObject t : heapObjects.values()) {
-            visitor.t = t;
-            // call addReferenceFrom(t) on all objects t references:
-            t.visitReferencedObjects(visitor);
-            ++count;
-            if (count % DOT_LIMIT == 0) {
-                System.out.print(".");
-                System.out.flush();
-            }
-        }
-        System.out.println();
-        for (Root r : roots) {
-            r.resolve(this);
-            JavaHeapObject t = findThing(r.getId());
-            if (t != null) {
-                t.addReferenceFromRoot(r);
-            }
-        }
-    }
-
-    public void markNewRelativeTo(Snapshot baseline) {
-        hasNewSet = true;
-        for (JavaHeapObject t : heapObjects.values()) {
-            boolean isNew;
-            long thingID = t.getId();
-            if (thingID == 0L || thingID == -1L) {
-                isNew = false;
-            } else {
-                JavaThing other = baseline.findThing(t.getId());
-                if (other == null) {
-                    isNew = true;
-                } else {
-                    isNew = !t.isSameTypeAs(other);
-                }
-            }
-            t.setNew(isNew);
-        }
-    }
-
-    public Enumeration<JavaHeapObject> getThings() {
-        return heapObjects.elements();
-    }
-
-
-    public JavaHeapObject findThing(long id) {
-        Number idObj = makeId(id);
-        JavaHeapObject jho = heapObjects.get(idObj);
-        return jho != null? jho : fakeClasses.get(idObj);
-    }
-
-    public JavaHeapObject findThing(String id) {
-        return findThing(Misc.parseHex(id));
-    }
-
-    public JavaClass findClass(String name) {
-        if (name.startsWith("0x")) {
-            return (JavaClass) findThing(name);
-        } else {
-            return classes.get(name);
-        }
-    }
-
-    /**
-     * Return an Iterator of all of the classes in this snapshot.
-     **/
-    public Iterator<JavaClass> getClasses() {
-        // note that because classes is a TreeMap
-        // classes are already sorted by name
-        return classes.values().iterator();
-    }
-
-    public JavaClass[] getClassesArray() {
-        JavaClass[] res = new JavaClass[classes.size()];
-        classes.values().toArray(res);
-        return res;
-    }
-
-    public synchronized Enumeration<?> getFinalizerObjects() {
-        Vector<?> obj;
-        if (finalizablesCache != null &&
-            (obj = finalizablesCache.get()) != null) {
-            return obj.elements();
-        }
-
-        JavaClass clazz = findClass("java.lang.ref.Finalizer");
-        JavaObject queue = (JavaObject) clazz.getStaticField("queue");
-        JavaThing tmp = queue.getField("head");
-        Vector<JavaHeapObject> finalizables = new Vector<JavaHeapObject>();
-        if (tmp != getNullThing()) {
-            JavaObject head = (JavaObject) tmp;
-            while (true) {
-                JavaHeapObject referent = (JavaHeapObject) head.getField("referent");
-                JavaThing next = head.getField("next");
-                if (next == getNullThing() || next.equals(head)) {
-                    break;
-                }
-                head = (JavaObject) next;
-                finalizables.add(referent);
-            }
-        }
-        finalizablesCache = new SoftReference<Vector<?>>(finalizables);
-        return finalizables.elements();
-    }
-
-    public Enumeration<Root> getRoots() {
-        return roots.elements();
-    }
-
-    public Root[] getRootsArray() {
-        Root[] res = new Root[roots.size()];
-        roots.toArray(res);
-        return res;
-    }
-
-    public Root getRootAt(int i) {
-        return roots.elementAt(i);
-    }
-
-    public ReferenceChain[]
-    rootsetReferencesTo(JavaHeapObject target, boolean includeWeak) {
-        Vector<ReferenceChain> fifo = new Vector<ReferenceChain>();  // This is slow... A real fifo would help
-            // Must be a fifo to go breadth-first
-        Hashtable<JavaHeapObject, JavaHeapObject> visited = new Hashtable<JavaHeapObject, JavaHeapObject>();
-        // Objects are added here right after being added to fifo.
-        Vector<ReferenceChain> result = new Vector<ReferenceChain>();
-        visited.put(target, target);
-        fifo.addElement(new ReferenceChain(target, null));
-
-        while (fifo.size() > 0) {
-            ReferenceChain chain = fifo.elementAt(0);
-            fifo.removeElementAt(0);
-            JavaHeapObject curr = chain.getObj();
-            if (curr.getRoot() != null) {
-                result.addElement(chain);
-                // Even though curr is in the rootset, we want to explore its
-                // referers, because they might be more interesting.
-            }
-            Enumeration<JavaThing> referers = curr.getReferers();
-            while (referers.hasMoreElements()) {
-                JavaHeapObject t = (JavaHeapObject) referers.nextElement();
-                if (t != null && !visited.containsKey(t)) {
-                    if (includeWeak || !t.refersOnlyWeaklyTo(this, curr)) {
-                        visited.put(t, t);
-                        fifo.addElement(new ReferenceChain(t, chain));
-                    }
-                }
-            }
-        }
-
-        ReferenceChain[] realResult = new ReferenceChain[result.size()];
-        for (int i = 0; i < result.size(); i++) {
-            realResult[i] =  result.elementAt(i);
-        }
-        return realResult;
-    }
-
-    public boolean getUnresolvedObjectsOK() {
-        return unresolvedObjectsOK;
-    }
-
-    public void setUnresolvedObjectsOK(boolean v) {
-        unresolvedObjectsOK = v;
-    }
-
-    public JavaClass getWeakReferenceClass() {
-        return weakReferenceClass;
-    }
-
-    public int getReferentFieldIndex() {
-        return referentFieldIndex;
-    }
-
-    public JavaThing getNullThing() {
-        return nullThing;
-    }
-
-    public void setReachableExcludes(ReachableExcludes e) {
-        reachableExcludes = e;
-    }
-
-    public ReachableExcludes getReachableExcludes() {
-        return reachableExcludes;
-    }
-
-    // package privates
-    void addReferenceFromRoot(Root r, JavaHeapObject obj) {
-        Root root = rootsMap.get(obj);
-        if (root == null) {
-            rootsMap.put(obj, r);
-        } else {
-            rootsMap.put(obj, root.mostInteresting(r));
-        }
-    }
-
-    Root getRoot(JavaHeapObject obj) {
-        return rootsMap.get(obj);
-    }
-
-    JavaClass getJavaLangClass() {
-        return javaLangClass;
-    }
-
-    JavaClass getJavaLangString() {
-        return javaLangString;
-    }
-
-    JavaClass getJavaLangClassLoader() {
-        return javaLangClassLoader;
-    }
-
-    JavaClass getOtherArrayType() {
-        if (otherArrayType == null) {
-            synchronized(this) {
-                if (otherArrayType == null) {
-                    addFakeClass(new JavaClass("[<other>", 0, 0, 0, 0,
-                                     EMPTY_FIELD_ARRAY, EMPTY_STATIC_ARRAY,
-                                     0));
-                    otherArrayType = findClass("[<other>");
-                }
-            }
-        }
-        return otherArrayType;
-    }
-
-    JavaClass getArrayClass(String elementSignature) {
-        JavaClass clazz;
-        synchronized(classes) {
-            clazz = findClass("[" + elementSignature);
-            if (clazz == null) {
-                clazz = new JavaClass("[" + elementSignature, 0, 0, 0, 0,
-                                   EMPTY_FIELD_ARRAY, EMPTY_STATIC_ARRAY, 0);
-                addFakeClass(clazz);
-                // This is needed because the JDK only creates Class structures
-                // for array element types, not the arrays themselves.  For
-                // analysis, though, we need to pretend that there's a
-                // JavaClass for the array type, too.
-            }
-        }
-        return clazz;
-    }
-
-    ReadBuffer getReadBuffer() {
-        return readBuf;
-    }
-
-    void setNew(JavaHeapObject obj, boolean isNew) {
-        initNewObjects();
-        if (isNew) {
-            newObjects.put(obj, Boolean.TRUE);
-        }
-    }
-
-    boolean isNew(JavaHeapObject obj) {
-        if (newObjects != null) {
-            return newObjects.get(obj) != null;
-        } else {
-            return false;
-        }
-    }
-
-    // Internals only below this point
-    private Number makeId(long id) {
-        if (identifierSize == 4) {
-            return (int)id;
-        } else {
-            return id;
-        }
-    }
-
-    private void putInClassesMap(JavaClass c) {
-        String name = c.getName();
-        if (classes.containsKey(name)) {
-            // more than one class can have the same name
-            // if so, create a unique name by appending
-            // - and id string to it.
-            name += "-" + c.getIdString();
-        }
-        classes.put(c.getName(), c);
-    }
-
-    private void addFakeClass(JavaClass c) {
-        putInClassesMap(c);
-        c.resolve(this);
-    }
-
-    private void addFakeClass(Number id, JavaClass c) {
-        fakeClasses.put(id, c);
-        addFakeClass(c);
-    }
-
-    private synchronized void initNewObjects() {
-        if (newObjects == null) {
-            synchronized (this) {
-                if (newObjects == null) {
-                    newObjects = new HashMap<JavaHeapObject, Boolean>();
-                }
-            }
-        }
-    }
-
-    private synchronized void initSiteTraces() {
-        if (siteTraces == null) {
-            synchronized (this) {
-                if (siteTraces == null) {
-                    siteTraces = new HashMap<JavaHeapObject, StackTrace>();
-                }
-            }
-        }
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/StackFrame.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,101 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-/**
- *
- * @author      Bill Foote
- */
-
-
-/**
- * Represents a stack frame.
- */
-
-public class StackFrame {
-
-    //
-    // Values for the lineNumber data member.  These are the same
-    // as the values used in the JDK 1.2 heap dump file.
-    //
-    public final static int LINE_NUMBER_UNKNOWN = -1;
-    public final static int LINE_NUMBER_COMPILED = -2;
-    public final static int LINE_NUMBER_NATIVE = -3;
-
-    private String methodName;
-    private String methodSignature;
-    private String className;
-    private String sourceFileName;
-    private int lineNumber;
-
-    public StackFrame(String methodName, String methodSignature,
-                      String className, String sourceFileName, int lineNumber) {
-        this.methodName = methodName;
-        this.methodSignature = methodSignature;
-        this.className = className;
-        this.sourceFileName = sourceFileName;
-        this.lineNumber = lineNumber;
-    }
-
-    public void resolve(Snapshot snapshot) {
-    }
-
-    public String getMethodName() {
-        return methodName;
-    }
-
-    public String getMethodSignature() {
-        return methodSignature;
-    }
-
-    public String getClassName() {
-        return className;
-    }
-
-    public String getSourceFileName() {
-        return sourceFileName;
-    }
-
-    public String getLineNumber() {
-        switch(lineNumber) {
-            case LINE_NUMBER_UNKNOWN:
-                return "(unknown)";
-            case LINE_NUMBER_COMPILED:
-                return "(compiled method)";
-            case LINE_NUMBER_NATIVE:
-                return "(native method)";
-            default:
-                return Integer.toString(lineNumber, 10);
-        }
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/model/StackTrace.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,77 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.model;
-
-/**
- *
- * @author      Bill Foote
- */
-
-
-/**
- * Represents a stack trace, that is, an ordered collection of stack frames.
- */
-
-public class StackTrace {
-
-    private StackFrame[] frames;
-
-    public StackTrace(StackFrame[] frames) {
-        this.frames = frames;
-    }
-
-    /**
-     * @param depth.  The minimum reasonable depth is 1.
-     *
-     * @return a (possibly new) StackTrace that is limited to depth.
-     */
-    public StackTrace traceForDepth(int depth) {
-        if (depth >= frames.length) {
-            return this;
-        } else {
-            StackFrame[] f = new StackFrame[depth];
-            System.arraycopy(frames, 0, f, 0, depth);
-            return new StackTrace(f);
-        }
-    }
-
-    public void resolve(Snapshot snapshot) {
-        for (int i = 0; i < frames.length; i++) {
-            frames[i].resolve(snapshot);
-        }
-    }
-
-    public StackFrame[] getFrames() {
-        return frames;
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/oql/OQLEngine.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,311 +0,0 @@
-/*
- * Copyright (c) 1997, 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.oql;
-
-import com.sun.tools.hat.internal.model.*;
-import java.io.*;
-import java.lang.reflect.*;
-import java.util.*;
-
-/**
- * This is Object Query Language Interpreter
- *
- */
-public class OQLEngine {
-    static {
-        try {
-            // Do we have javax.script support?
-            // create ScriptEngineManager
-            Class<?> managerClass = Class.forName("javax.script.ScriptEngineManager");
-            Object manager = managerClass.newInstance();
-
-            // create JavaScript engine
-            Method getEngineMethod = managerClass.getMethod("getEngineByName",
-                                new Class<?>[] { String.class });
-            Object jse = getEngineMethod.invoke(manager, new Object[] {"js"});
-            oqlSupported = (jse != null);
-        } catch (Exception exp) {
-            oqlSupported = false;
-        }
-    }
-
-    // check OQL is supported or not before creating OQLEngine
-    public static boolean isOQLSupported() {
-        return oqlSupported;
-    }
-
-    public OQLEngine(Snapshot snapshot) {
-        if (!isOQLSupported()) {
-            throw new UnsupportedOperationException("OQL not supported");
-        }
-        init(snapshot);
-    }
-
-    /**
-       Query is of the form
-
-          select &lt;java script code to select&gt;
-          [ from [instanceof] &lt;class name&gt; [&lt;identifier&gt;]
-            [ where &lt;java script boolean expression&gt; ]
-          ]
-    */
-    public synchronized void executeQuery(String query, ObjectVisitor visitor)
-                                          throws OQLException {
-        debugPrint("query : " + query);
-        StringTokenizer st = new StringTokenizer(query);
-        if (st.hasMoreTokens()) {
-            String first = st.nextToken();
-            if (! first.equals("select") ) {
-                // Query does not start with 'select' keyword.
-                // Just treat it as plain JavaScript and eval it.
-                try {
-                    Object res = evalScript(query);
-                    visitor.visit(res);
-                } catch (Exception e) {
-                    throw new OQLException(e);
-                }
-                return;
-            }
-        } else {
-            throw new OQLException("query syntax error: no 'select' clause");
-        }
-
-        String selectExpr = "";
-        boolean seenFrom = false;
-        while (st.hasMoreTokens()) {
-            String tok = st.nextToken();
-            if (tok.equals("from")) {
-                seenFrom = true;
-                break;
-            }
-            selectExpr += " " + tok;
-        }
-
-        if (selectExpr.equals("")) {
-            throw new OQLException("query syntax error: 'select' expression can not be empty");
-        }
-
-        String className = null;
-        boolean isInstanceOf = false;
-        String whereExpr =  null;
-        String identifier = null;
-
-        if (seenFrom) {
-            if (st.hasMoreTokens()) {
-                String tmp = st.nextToken();
-                if (tmp.equals("instanceof")) {
-                    isInstanceOf = true;
-                    if (! st.hasMoreTokens()) {
-                        throw new OQLException("no class name after 'instanceof'");
-                    }
-                    className = st.nextToken();
-                } else {
-                    className = tmp;
-                }
-            } else {
-                throw new OQLException("query syntax error: class name must follow 'from'");
-            }
-
-            if (st.hasMoreTokens()) {
-                identifier = st.nextToken();
-                if (identifier.equals("where")) {
-                    throw new OQLException("query syntax error: identifier should follow class name");
-                }
-                if (st.hasMoreTokens()) {
-                    String tmp = st.nextToken();
-                    if (! tmp.equals("where")) {
-                        throw new OQLException("query syntax error: 'where' clause expected after 'from' clause");
-                    }
-
-                    whereExpr = "";
-                    while (st.hasMoreTokens()) {
-                        whereExpr += " " + st.nextToken();
-                    }
-                    if (whereExpr.equals("")) {
-                        throw new OQLException("query syntax error: 'where' clause cannot have empty expression");
-                    }
-                }
-            } else {
-                throw new OQLException("query syntax error: identifier should follow class name");
-            }
-        }
-
-        executeQuery(new OQLQuery(selectExpr, isInstanceOf, className,
-                                  identifier, whereExpr), visitor);
-    }
-
-    private void executeQuery(OQLQuery q, ObjectVisitor visitor)
-                              throws OQLException {
-        JavaClass clazz = null;
-        if (q.className != null) {
-            clazz = snapshot.findClass(q.className);
-            if (clazz == null) {
-                throw new OQLException(q.className + " is not found!");
-            }
-        }
-
-        StringBuffer buf = new StringBuffer();
-        buf.append("function __select__(");
-        if (q.identifier != null) {
-            buf.append(q.identifier);
-        }
-        buf.append(") { return ");
-        buf.append(q.selectExpr.replace('\n', ' '));
-        buf.append("; }");
-
-        String selectCode = buf.toString();
-        debugPrint(selectCode);
-        String whereCode = null;
-        if (q.whereExpr != null) {
-            buf = new StringBuffer();
-            buf.append("function __where__(");
-            buf.append(q.identifier);
-            buf.append(") { return ");
-            buf.append(q.whereExpr.replace('\n', ' '));
-            buf.append("; }");
-            whereCode = buf.toString();
-        }
-        debugPrint(whereCode);
-
-        // compile select expression and where condition
-        try {
-            evalMethod.invoke(engine, new Object[] { selectCode });
-            if (whereCode != null) {
-                evalMethod.invoke(engine, new Object[] { whereCode });
-            }
-
-            if (q.className != null) {
-                Enumeration<JavaHeapObject> objects = clazz.getInstances(q.isInstanceOf);
-                while (objects.hasMoreElements()) {
-                    JavaHeapObject obj = objects.nextElement();
-                    Object[] args = new Object[] { wrapJavaObject(obj) };
-                    boolean b = (whereCode == null);
-                    if (!b) {
-                        Object res = call("__where__", args);
-                        if (res instanceof Boolean) {
-                            b = ((Boolean)res).booleanValue();
-                        } else if (res instanceof Number) {
-                            b = ((Number)res).intValue() != 0;
-                        } else {
-                            b = (res != null);
-                        }
-                    }
-
-                    if (b) {
-                        Object select = call("__select__", args);
-                        if (visitor.visit(select)) return;
-                    }
-                }
-            } else {
-                // simple "select <expr>" query
-                Object select = call("__select__", new Object[] {});
-                visitor.visit(select);
-            }
-        } catch (Exception e) {
-            throw new OQLException(e);
-        }
-    }
-
-    public Object evalScript(String script) throws Exception {
-        return evalMethod.invoke(engine, new Object[] { script });
-    }
-
-    public Object wrapJavaObject(JavaHeapObject obj) throws Exception {
-        return call("wrapJavaObject", new Object[] { obj });
-    }
-
-    public Object toHtml(Object obj) throws Exception {
-        return call("toHtml", new Object[] { obj });
-    }
-
-    public Object call(String func, Object[] args) throws Exception {
-        return invokeMethod.invoke(engine, new Object[] { func, args });
-    }
-
-    private static void debugPrint(String msg) {
-        if (debug) System.out.println(msg);
-    }
-
-    private void init(Snapshot snapshot) throws RuntimeException {
-        this.snapshot = snapshot;
-        try {
-            // create ScriptEngineManager
-            Class<?> managerClass = Class.forName("javax.script.ScriptEngineManager");
-            Object manager = managerClass.newInstance();
-
-            // create JavaScript engine
-            Method getEngineMethod = managerClass.getMethod("getEngineByName",
-                                new Class<?>[] { String.class });
-            engine = getEngineMethod.invoke(manager, new Object[] {"js"});
-
-            // initialize engine with init file (hat.js)
-            InputStream strm = getInitStream();
-            Class<?> engineClass = Class.forName("javax.script.ScriptEngine");
-            evalMethod = engineClass.getMethod("eval",
-                                new Class<?>[] { Reader.class });
-            evalMethod.invoke(engine, new Object[] {new InputStreamReader(strm)});
-
-            // initialize ScriptEngine.eval(String) and
-            // Invocable.invokeFunction(String, Object[]) methods.
-            Class<?> invocableClass = Class.forName("javax.script.Invocable");
-
-            evalMethod = engineClass.getMethod("eval",
-                                  new Class<?>[] { String.class });
-            invokeMethod = invocableClass.getMethod("invokeFunction",
-                                  new Class<?>[] { String.class, Object[].class });
-
-            // initialize ScriptEngine.put(String, Object) method
-            Method putMethod = engineClass.getMethod("put",
-                                  new Class<?>[] { String.class, Object.class });
-
-            // call ScriptEngine.put to initialize built-in heap object
-            putMethod.invoke(engine, new Object[] {
-                        "heap", call("wrapHeapSnapshot", new Object[] { snapshot })
-                    });
-        } catch (Exception e) {
-            if (debug) e.printStackTrace();
-            throw new RuntimeException(e);
-        }
-    }
-
-    private InputStream getInitStream() {
-        return getClass().getResourceAsStream("/com/sun/tools/hat/resources/hat.js");
-    }
-
-    private Object engine;
-    private Method evalMethod;
-    private Method invokeMethod;
-    private Snapshot snapshot;
-    private static boolean debug = false;
-    private static boolean oqlSupported;
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/oql/OQLException.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,52 +0,0 @@
-/*
- * Copyright (c) 1997, 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.oql;
-
-/**
- * OQLException is thrown if OQL execution results in error
- *
- */
-@SuppressWarnings("serial") // JDK implementation class
-public class OQLException extends Exception {
-    public OQLException(String msg) {
-        super(msg);
-    }
-
-    public OQLException(String msg, Throwable cause) {
-        super(msg, cause);
-    }
-
-    public OQLException(Throwable cause) {
-        super(cause);
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/oql/OQLQuery.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,54 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.oql;
-
-/**
- * This represents a parsed OQL query
- *
- */
-class OQLQuery {
-    OQLQuery(String selectExpr, boolean isInstanceOf,
-             String className, String identifier, String whereExpr) {
-        this.selectExpr = selectExpr;
-        this.isInstanceOf = isInstanceOf;
-        this.className = className;
-        this.identifier = identifier;
-        this.whereExpr = whereExpr;
-    }
-
-    String   selectExpr;
-    boolean  isInstanceOf;
-    String   className;
-    String   identifier;
-    String   whereExpr;
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/oql/ObjectVisitor.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,43 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.oql;
-
-/**
- * This visitor is supplied to OQLEngine.executeQuery
- * to receive result set objects one by one.
- *
- */
-public interface ObjectVisitor {
-    // return true to terminate the result set callback earlier
-    public boolean visit(Object o);
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/parser/FileReadBuffer.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,84 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.parser;
-
-import java.io.IOException;
-import java.io.RandomAccessFile;
-
-/**
- * Implementation of ReadBuffer using a RandomAccessFile
- *
- * @author A. Sundararajan
- */
-class FileReadBuffer implements ReadBuffer {
-    // underlying file to read
-    private RandomAccessFile file;
-
-    FileReadBuffer(RandomAccessFile file) {
-        this.file = file;
-    }
-
-    private void seek(long pos) throws IOException {
-        file.getChannel().position(pos);
-    }
-
-    public synchronized void get(long pos, byte[] buf) throws IOException {
-        seek(pos);
-        file.read(buf);
-    }
-
-    public synchronized char getChar(long pos) throws IOException {
-        seek(pos);
-        return file.readChar();
-    }
-
-    public synchronized byte getByte(long pos) throws IOException {
-        seek(pos);
-        return (byte) file.read();
-    }
-
-    public synchronized short getShort(long pos) throws IOException {
-        seek(pos);
-        return file.readShort();
-    }
-
-    public synchronized int getInt(long pos) throws IOException {
-        seek(pos);
-        return file.readInt();
-    }
-
-    public synchronized long getLong(long pos) throws IOException {
-        seek(pos);
-        return file.readLong();
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/parser/HprofReader.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,892 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.parser;
-
-import java.io.*;
-import java.util.Date;
-import java.util.Hashtable;
-import com.sun.tools.hat.internal.model.ArrayTypeCodes;
-import com.sun.tools.hat.internal.model.*;
-
-/**
- * Object that's used to read a hprof file.
- *
- * @author      Bill Foote
- */
-
-public class HprofReader extends Reader /* imports */ implements ArrayTypeCodes {
-
-    final static int MAGIC_NUMBER = 0x4a415641;
-    // That's "JAVA", the first part of "JAVA PROFILE ..."
-    private final static String[] VERSIONS = {
-            " PROFILE 1.0\0",
-            " PROFILE 1.0.1\0",
-            " PROFILE 1.0.2\0",
-    };
-
-    private final static int VERSION_JDK12BETA3 = 0;
-    private final static int VERSION_JDK12BETA4 = 1;
-    private final static int VERSION_JDK6       = 2;
-    // These version numbers are indices into VERSIONS.  The instance data
-    // member version is set to one of these, and it drives decisions when
-    // reading the file.
-    //
-    // Version 1.0.1 added HPROF_GC_PRIM_ARRAY_DUMP, which requires no
-    // version-sensitive parsing.
-    //
-    // Version 1.0.1 changed the type of a constant pool entry from a signature
-    // to a typecode.
-    //
-    // Version 1.0.2 added HPROF_HEAP_DUMP_SEGMENT and HPROF_HEAP_DUMP_END
-    // to allow a large heap to be dumped as a sequence of heap dump segments.
-    //
-    // The HPROF agent in J2SE 1.2 through to 5.0 generate a version 1.0.1
-    // file. In Java SE 6.0 the version is either 1.0.1 or 1.0.2 depending on
-    // the size of the heap (normally it will be 1.0.1 but for multi-GB
-    // heaps the heap dump will not fit in a HPROF_HEAP_DUMP record so the
-    // dump is generated as version 1.0.2).
-
-    //
-    // Record types:
-    //
-    static final int HPROF_UTF8          = 0x01;
-    static final int HPROF_LOAD_CLASS    = 0x02;
-    static final int HPROF_UNLOAD_CLASS  = 0x03;
-    static final int HPROF_FRAME         = 0x04;
-    static final int HPROF_TRACE         = 0x05;
-    static final int HPROF_ALLOC_SITES   = 0x06;
-    static final int HPROF_HEAP_SUMMARY  = 0x07;
-
-    static final int HPROF_START_THREAD  = 0x0a;
-    static final int HPROF_END_THREAD    = 0x0b;
-
-    static final int HPROF_HEAP_DUMP     = 0x0c;
-
-    static final int HPROF_CPU_SAMPLES   = 0x0d;
-    static final int HPROF_CONTROL_SETTINGS = 0x0e;
-    static final int HPROF_LOCKSTATS_WAIT_TIME = 0x10;
-    static final int HPROF_LOCKSTATS_HOLD_TIME = 0x11;
-
-    static final int HPROF_GC_ROOT_UNKNOWN       = 0xff;
-    static final int HPROF_GC_ROOT_JNI_GLOBAL    = 0x01;
-    static final int HPROF_GC_ROOT_JNI_LOCAL     = 0x02;
-    static final int HPROF_GC_ROOT_JAVA_FRAME    = 0x03;
-    static final int HPROF_GC_ROOT_NATIVE_STACK  = 0x04;
-    static final int HPROF_GC_ROOT_STICKY_CLASS  = 0x05;
-    static final int HPROF_GC_ROOT_THREAD_BLOCK  = 0x06;
-    static final int HPROF_GC_ROOT_MONITOR_USED  = 0x07;
-    static final int HPROF_GC_ROOT_THREAD_OBJ    = 0x08;
-
-    static final int HPROF_GC_CLASS_DUMP         = 0x20;
-    static final int HPROF_GC_INSTANCE_DUMP      = 0x21;
-    static final int HPROF_GC_OBJ_ARRAY_DUMP         = 0x22;
-    static final int HPROF_GC_PRIM_ARRAY_DUMP         = 0x23;
-
-    static final int HPROF_HEAP_DUMP_SEGMENT     = 0x1c;
-    static final int HPROF_HEAP_DUMP_END         = 0x2c;
-
-    private final static int T_CLASS = 2;
-
-    private int version;        // The version of .hprof being read
-
-    private int debugLevel;
-    private long currPos;        // Current position in the file
-
-    private int dumpsToSkip;
-    private boolean callStack;  // If true, read the call stack of objects
-
-    private int identifierSize;         // Size, in bytes, of identifiers.
-    private Hashtable<Long, String> names;
-
-    // Hashtable<Integer, ThreadObject>, used to map the thread sequence number
-    // (aka "serial number") to the thread object ID for
-    // HPROF_GC_ROOT_THREAD_OBJ.  ThreadObject is a trivial inner class,
-    // at the end of this file.
-    private Hashtable<Integer, ThreadObject> threadObjects;
-
-    // Hashtable<Long, String>, maps class object ID to class name
-    // (with / converted to .)
-    private Hashtable<Long, String> classNameFromObjectID;
-
-    // Hashtable<Integer, Integer>, maps class serial # to class object ID
-    private Hashtable<Integer, String> classNameFromSerialNo;
-
-    // Hashtable<Long, StackFrame> maps stack frame ID to StackFrame.
-    // Null if we're not tracking them.
-    private Hashtable<Long, StackFrame> stackFrames;
-
-    // Hashtable<Integer, StackTrace> maps stack frame ID to StackTrace
-    // Null if we're not tracking them.
-    private Hashtable<Integer, StackTrace> stackTraces;
-
-    private Snapshot snapshot;
-
-    public HprofReader(String fileName, PositionDataInputStream in,
-                       int dumpNumber, boolean callStack, int debugLevel)
-                       throws IOException {
-        super(in);
-        RandomAccessFile file = new RandomAccessFile(fileName, "r");
-        this.snapshot = new Snapshot(MappedReadBuffer.create(file));
-        this.dumpsToSkip = dumpNumber - 1;
-        this.callStack = callStack;
-        this.debugLevel = debugLevel;
-        names = new Hashtable<Long, String>();
-        threadObjects = new Hashtable<Integer, ThreadObject>(43);
-        classNameFromObjectID = new Hashtable<Long, String>();
-        if (callStack) {
-            stackFrames = new Hashtable<Long, StackFrame>(43);
-            stackTraces = new Hashtable<Integer, StackTrace>(43);
-            classNameFromSerialNo = new Hashtable<Integer, String>();
-        }
-    }
-
-    public Snapshot read() throws IOException {
-        currPos = 4;    // 4 because of the magic number
-        version = readVersionHeader();
-        identifierSize = in.readInt();
-        snapshot.setIdentifierSize(identifierSize);
-        if (version >= VERSION_JDK12BETA4) {
-            snapshot.setNewStyleArrayClass(true);
-        } else {
-            snapshot.setNewStyleArrayClass(false);
-        }
-
-        currPos += 4;
-        if (identifierSize != 4 && identifierSize != 8) {
-            throw new IOException("I'm sorry, but I can't deal with an identifier size of " + identifierSize + ".  I can only deal with 4 or 8.");
-        }
-        System.out.println("Dump file created " + (new Date(in.readLong())));
-        currPos += 8;
-
-        for (;;) {
-            int type;
-            try {
-                type = in.readUnsignedByte();
-            } catch (EOFException ignored) {
-                break;
-            }
-            in.readInt();       // Timestamp of this record
-            // Length of record: readInt() will return negative value for record
-            // length >2GB.  so store 32bit value in long to keep it unsigned.
-            long length = in.readInt() & 0xffffffffL;
-            if (debugLevel > 0) {
-                System.out.println("Read record type " + type
-                                   + ", length " + length
-                                   + " at position " + toHex(currPos));
-            }
-            if (length < 0) {
-                throw new IOException("Bad record length of " + length
-                                      + " at byte " + toHex(currPos+5)
-                                      + " of file.");
-            }
-            currPos += 9 + length;
-            switch (type) {
-                case HPROF_UTF8: {
-                    long id = readID();
-                    byte[] chars = new byte[(int)length - identifierSize];
-                    in.readFully(chars);
-                    names.put(id, new String(chars));
-                    break;
-                }
-                case HPROF_LOAD_CLASS: {
-                    int serialNo = in.readInt();        // Not used
-                    long classID = readID();
-                    int stackTraceSerialNo = in.readInt();
-                    long classNameID = readID();
-                    Long classIdI = classID;
-                    String nm = getNameFromID(classNameID).replace('/', '.');
-                    classNameFromObjectID.put(classIdI, nm);
-                    if (classNameFromSerialNo != null) {
-                        classNameFromSerialNo.put(serialNo, nm);
-                    }
-                    break;
-                }
-
-                case HPROF_HEAP_DUMP: {
-                    if (dumpsToSkip <= 0) {
-                        try {
-                            readHeapDump(length, currPos);
-                        } catch (EOFException exp) {
-                            handleEOF(exp, snapshot);
-                        }
-                        if (debugLevel > 0) {
-                            System.out.println("    Finished processing instances in heap dump.");
-                        }
-                        return snapshot;
-                    } else {
-                        dumpsToSkip--;
-                        skipBytes(length);
-                    }
-                    break;
-                }
-
-                case HPROF_HEAP_DUMP_END: {
-                    if (version >= VERSION_JDK6) {
-                        if (dumpsToSkip <= 0) {
-                            skipBytes(length);  // should be no-op
-                            return snapshot;
-                        } else {
-                            // skip this dump (of the end record for a sequence of dump segments)
-                            dumpsToSkip--;
-                        }
-                    } else {
-                        // HPROF_HEAP_DUMP_END only recognized in >= 1.0.2
-                        warn("Ignoring unrecognized record type " + type);
-                    }
-                    skipBytes(length);  // should be no-op
-                    break;
-                }
-
-                case HPROF_HEAP_DUMP_SEGMENT: {
-                    if (version >= VERSION_JDK6) {
-                        if (dumpsToSkip <= 0) {
-                            try {
-                                // read the dump segment
-                                readHeapDump(length, currPos);
-                            } catch (EOFException exp) {
-                                handleEOF(exp, snapshot);
-                            }
-                        } else {
-                            // all segments comprising the heap dump will be skipped
-                            skipBytes(length);
-                        }
-                    } else {
-                        // HPROF_HEAP_DUMP_SEGMENT only recognized in >= 1.0.2
-                        warn("Ignoring unrecognized record type " + type);
-                        skipBytes(length);
-                    }
-                    break;
-                }
-
-                case HPROF_FRAME: {
-                    if (stackFrames == null) {
-                        skipBytes(length);
-                    } else {
-                        long id = readID();
-                        String methodName = getNameFromID(readID());
-                        String methodSig = getNameFromID(readID());
-                        String sourceFile = getNameFromID(readID());
-                        int classSer = in.readInt();
-                        String className = classNameFromSerialNo.get(classSer);
-                        int lineNumber = in.readInt();
-                        if (lineNumber < StackFrame.LINE_NUMBER_NATIVE) {
-                            warn("Weird stack frame line number:  " + lineNumber);
-                            lineNumber = StackFrame.LINE_NUMBER_UNKNOWN;
-                        }
-                        stackFrames.put(id,
-                                        new StackFrame(methodName, methodSig,
-                                                       className, sourceFile,
-                                                       lineNumber));
-                    }
-                    break;
-                }
-                case HPROF_TRACE: {
-                    if (stackTraces == null) {
-                        skipBytes(length);
-                    } else {
-                        int serialNo = in.readInt();
-                        int threadSeq = in.readInt();   // Not used
-                        StackFrame[] frames = new StackFrame[in.readInt()];
-                        for (int i = 0; i < frames.length; i++) {
-                            long fid = readID();
-                            frames[i] = stackFrames.get(fid);
-                            if (frames[i] == null) {
-                                throw new IOException("Stack frame " + toHex(fid) + " not found");
-                            }
-                        }
-                        stackTraces.put(serialNo,
-                                        new StackTrace(frames));
-                    }
-                    break;
-                }
-                case HPROF_UNLOAD_CLASS:
-                case HPROF_ALLOC_SITES:
-                case HPROF_START_THREAD:
-                case HPROF_END_THREAD:
-                case HPROF_HEAP_SUMMARY:
-                case HPROF_CPU_SAMPLES:
-                case HPROF_CONTROL_SETTINGS:
-                case HPROF_LOCKSTATS_WAIT_TIME:
-                case HPROF_LOCKSTATS_HOLD_TIME:
-                {
-                    // Ignore these record types
-                    skipBytes(length);
-                    break;
-                }
-                default: {
-                    skipBytes(length);
-                    warn("Ignoring unrecognized record type " + type);
-                }
-            }
-        }
-
-        return snapshot;
-    }
-
-    private void skipBytes(long length) throws IOException {
-        in.skipBytes((int)length);
-    }
-
-    private int readVersionHeader() throws IOException {
-        int candidatesLeft = VERSIONS.length;
-        boolean[] matched = new boolean[VERSIONS.length];
-        for (int i = 0; i < candidatesLeft; i++) {
-            matched[i] = true;
-        }
-
-        int pos = 0;
-        while (candidatesLeft > 0) {
-            char c = (char) in.readByte();
-            currPos++;
-            for (int i = 0; i < VERSIONS.length; i++) {
-                if (matched[i]) {
-                    if (c != VERSIONS[i].charAt(pos)) {   // Not matched
-                        matched[i] = false;
-                        --candidatesLeft;
-                    } else if (pos == VERSIONS[i].length() - 1) {  // Full match
-                        return i;
-                    }
-                }
-            }
-            ++pos;
-        }
-        throw new IOException("Version string not recognized at byte " + (pos+3));
-    }
-
-    private void readHeapDump(long bytesLeft, long posAtEnd) throws IOException {
-        while (bytesLeft > 0) {
-            int type = in.readUnsignedByte();
-            if (debugLevel > 0) {
-                System.out.println("    Read heap sub-record type " + type
-                                   + " at position "
-                                   + toHex(posAtEnd - bytesLeft));
-            }
-            bytesLeft--;
-            switch(type) {
-                case HPROF_GC_ROOT_UNKNOWN: {
-                    long id = readID();
-                    bytesLeft -= identifierSize;
-                    snapshot.addRoot(new Root(id, 0, Root.UNKNOWN, ""));
-                    break;
-                }
-                case HPROF_GC_ROOT_THREAD_OBJ: {
-                    long id = readID();
-                    int threadSeq = in.readInt();
-                    int stackSeq = in.readInt();
-                    bytesLeft -= identifierSize + 8;
-                    threadObjects.put(threadSeq,
-                                      new ThreadObject(id, stackSeq));
-                    break;
-                }
-                case HPROF_GC_ROOT_JNI_GLOBAL: {
-                    long id = readID();
-                    long globalRefId = readID();        // Ignored, for now
-                    bytesLeft -= 2*identifierSize;
-                    snapshot.addRoot(new Root(id, 0, Root.NATIVE_STATIC, ""));
-                    break;
-                }
-                case HPROF_GC_ROOT_JNI_LOCAL: {
-                    long id = readID();
-                    int threadSeq = in.readInt();
-                    int depth = in.readInt();
-                    bytesLeft -= identifierSize + 8;
-                    ThreadObject to = getThreadObjectFromSequence(threadSeq);
-                    StackTrace st = getStackTraceFromSerial(to.stackSeq);
-                    if (st != null) {
-                        st = st.traceForDepth(depth+1);
-                    }
-                    snapshot.addRoot(new Root(id, to.threadId,
-                                              Root.NATIVE_LOCAL, "", st));
-                    break;
-                }
-                case HPROF_GC_ROOT_JAVA_FRAME: {
-                    long id = readID();
-                    int threadSeq = in.readInt();
-                    int depth = in.readInt();
-                    bytesLeft -= identifierSize + 8;
-                    ThreadObject to = getThreadObjectFromSequence(threadSeq);
-                    StackTrace st = getStackTraceFromSerial(to.stackSeq);
-                    if (st != null) {
-                        st = st.traceForDepth(depth+1);
-                    }
-                    snapshot.addRoot(new Root(id, to.threadId,
-                                              Root.JAVA_LOCAL, "", st));
-                    break;
-                }
-                case HPROF_GC_ROOT_NATIVE_STACK: {
-                    long id = readID();
-                    int threadSeq = in.readInt();
-                    bytesLeft -= identifierSize + 4;
-                    ThreadObject to = getThreadObjectFromSequence(threadSeq);
-                    StackTrace st = getStackTraceFromSerial(to.stackSeq);
-                    snapshot.addRoot(new Root(id, to.threadId,
-                                              Root.NATIVE_STACK, "", st));
-                    break;
-                }
-                case HPROF_GC_ROOT_STICKY_CLASS: {
-                    long id = readID();
-                    bytesLeft -= identifierSize;
-                    snapshot.addRoot(new Root(id, 0, Root.SYSTEM_CLASS, ""));
-                    break;
-                }
-                case HPROF_GC_ROOT_THREAD_BLOCK: {
-                    long id = readID();
-                    int threadSeq = in.readInt();
-                    bytesLeft -= identifierSize + 4;
-                    ThreadObject to = getThreadObjectFromSequence(threadSeq);
-                    StackTrace st = getStackTraceFromSerial(to.stackSeq);
-                    snapshot.addRoot(new Root(id, to.threadId,
-                                     Root.THREAD_BLOCK, "", st));
-                    break;
-                }
-                case HPROF_GC_ROOT_MONITOR_USED: {
-                    long id = readID();
-                    bytesLeft -= identifierSize;
-                    snapshot.addRoot(new Root(id, 0, Root.BUSY_MONITOR, ""));
-                    break;
-                }
-                case HPROF_GC_CLASS_DUMP: {
-                    int bytesRead = readClass();
-                    bytesLeft -= bytesRead;
-                    break;
-                }
-                case HPROF_GC_INSTANCE_DUMP: {
-                    int bytesRead = readInstance();
-                    bytesLeft -= bytesRead;
-                    break;
-                }
-                case HPROF_GC_OBJ_ARRAY_DUMP: {
-                    int bytesRead = readArray(false);
-                    bytesLeft -= bytesRead;
-                    break;
-                }
-                case HPROF_GC_PRIM_ARRAY_DUMP: {
-                    int bytesRead = readArray(true);
-                    bytesLeft -= bytesRead;
-                    break;
-                }
-                default: {
-                    throw new IOException("Unrecognized heap dump sub-record type:  " + type);
-                }
-            }
-        }
-        if (bytesLeft != 0) {
-            warn("Error reading heap dump or heap dump segment:  Byte count is " + bytesLeft + " instead of 0");
-            skipBytes(bytesLeft);
-        }
-        if (debugLevel > 0) {
-            System.out.println("    Finished heap sub-records.");
-        }
-    }
-
-    private long readID() throws IOException {
-        return (identifierSize == 4)?
-            (Snapshot.SMALL_ID_MASK & (long)in.readInt()) : in.readLong();
-    }
-
-    //
-    // Read a java value.  If result is non-null, it's expected to be an
-    // array of one element.  We use it to fake multiple return values.
-    // @returns the number of bytes read
-    //
-    private int readValue(JavaThing[] resultArr) throws IOException {
-        byte type = in.readByte();
-        return 1 + readValueForType(type, resultArr);
-    }
-
-    private int readValueForType(byte type, JavaThing[] resultArr)
-            throws IOException {
-        if (version >= VERSION_JDK12BETA4) {
-            type = signatureFromTypeId(type);
-        }
-        return readValueForTypeSignature(type, resultArr);
-    }
-
-    private int readValueForTypeSignature(byte type, JavaThing[] resultArr)
-            throws IOException {
-        switch (type) {
-            case '[':
-            case 'L': {
-                long id = readID();
-                if (resultArr != null) {
-                    resultArr[0] = new JavaObjectRef(id);
-                }
-                return identifierSize;
-            }
-            case 'Z': {
-                int b = in.readByte();
-                if (b != 0 && b != 1) {
-                    warn("Illegal boolean value read");
-                }
-                if (resultArr != null) {
-                    resultArr[0] = new JavaBoolean(b != 0);
-                }
-                return 1;
-            }
-            case 'B': {
-                byte b = in.readByte();
-                if (resultArr != null) {
-                    resultArr[0] = new JavaByte(b);
-                }
-                return 1;
-            }
-            case 'S': {
-                short s = in.readShort();
-                if (resultArr != null) {
-                    resultArr[0] = new JavaShort(s);
-                }
-                return 2;
-            }
-            case 'C': {
-                char ch = in.readChar();
-                if (resultArr != null) {
-                    resultArr[0] = new JavaChar(ch);
-                }
-                return 2;
-            }
-            case 'I': {
-                int val = in.readInt();
-                if (resultArr != null) {
-                    resultArr[0] = new JavaInt(val);
-                }
-                return 4;
-            }
-            case 'J': {
-                long val = in.readLong();
-                if (resultArr != null) {
-                    resultArr[0] = new JavaLong(val);
-                }
-                return 8;
-            }
-            case 'F': {
-                float val = in.readFloat();
-                if (resultArr != null) {
-                    resultArr[0] = new JavaFloat(val);
-                }
-                return 4;
-            }
-            case 'D': {
-                double val = in.readDouble();
-                if (resultArr != null) {
-                    resultArr[0] = new JavaDouble(val);
-                }
-                return 8;
-            }
-            default: {
-                throw new IOException("Bad value signature:  " + type);
-            }
-        }
-    }
-
-    private ThreadObject getThreadObjectFromSequence(int threadSeq)
-            throws IOException {
-        ThreadObject to = threadObjects.get(threadSeq);
-        if (to == null) {
-            throw new IOException("Thread " + threadSeq +
-                                  " not found for JNI local ref");
-        }
-        return to;
-    }
-
-    private String getNameFromID(long id) throws IOException {
-        return getNameFromID(Long.valueOf(id));
-    }
-
-    private String getNameFromID(Long id) throws IOException {
-        if (id.longValue() == 0L) {
-            return "";
-        }
-        String result = names.get(id);
-        if (result == null) {
-            warn("Name not found at " + toHex(id.longValue()));
-            return "unresolved name " + toHex(id.longValue());
-        }
-        return result;
-    }
-
-    private StackTrace getStackTraceFromSerial(int ser) throws IOException {
-        if (stackTraces == null) {
-            return null;
-        }
-        StackTrace result = stackTraces.get(ser);
-        if (result == null) {
-            warn("Stack trace not found for serial # " + ser);
-        }
-        return result;
-    }
-
-    //
-    // Handle a HPROF_GC_CLASS_DUMP
-    // Return number of bytes read
-    //
-    private int readClass() throws IOException {
-        long id = readID();
-        StackTrace stackTrace = getStackTraceFromSerial(in.readInt());
-        long superId = readID();
-        long classLoaderId = readID();
-        long signersId = readID();
-        long protDomainId = readID();
-        long reserved1 = readID();
-        long reserved2 = readID();
-        int instanceSize = in.readInt();
-        int bytesRead = 7 * identifierSize + 8;
-
-        int numConstPoolEntries = in.readUnsignedShort();
-        bytesRead += 2;
-        for (int i = 0; i < numConstPoolEntries; i++) {
-            int index = in.readUnsignedShort(); // unused
-            bytesRead += 2;
-            bytesRead += readValue(null);       // We ignore the values
-        }
-
-        int numStatics = in.readUnsignedShort();
-        bytesRead += 2;
-        JavaThing[] valueBin = new JavaThing[1];
-        JavaStatic[] statics = new JavaStatic[numStatics];
-        for (int i = 0; i < numStatics; i++) {
-            long nameId = readID();
-            bytesRead += identifierSize;
-            byte type = in.readByte();
-            bytesRead++;
-            bytesRead += readValueForType(type, valueBin);
-            String fieldName = getNameFromID(nameId);
-            if (version >= VERSION_JDK12BETA4) {
-                type = signatureFromTypeId(type);
-            }
-            String signature = "" + ((char) type);
-            JavaField f = new JavaField(fieldName, signature);
-            statics[i] = new JavaStatic(f, valueBin[0]);
-        }
-
-        int numFields = in.readUnsignedShort();
-        bytesRead += 2;
-        JavaField[] fields = new JavaField[numFields];
-        for (int i = 0; i < numFields; i++) {
-            long nameId = readID();
-            bytesRead += identifierSize;
-            byte type = in.readByte();
-            bytesRead++;
-            String fieldName = getNameFromID(nameId);
-            if (version >= VERSION_JDK12BETA4) {
-                type = signatureFromTypeId(type);
-            }
-            String signature = "" + ((char) type);
-            fields[i] = new JavaField(fieldName, signature);
-        }
-        String name = classNameFromObjectID.get(id);
-        if (name == null) {
-            warn("Class name not found for " + toHex(id));
-            name = "unknown-name@" + toHex(id);
-        }
-        JavaClass c = new JavaClass(id, name, superId, classLoaderId, signersId,
-                                    protDomainId, fields, statics,
-                                    instanceSize);
-        snapshot.addClass(id, c);
-        snapshot.setSiteTrace(c, stackTrace);
-
-        return bytesRead;
-    }
-
-    private String toHex(long addr) {
-        return com.sun.tools.hat.internal.util.Misc.toHex(addr);
-    }
-
-    //
-    // Handle a HPROF_GC_INSTANCE_DUMP
-    // Return number of bytes read
-    //
-    private int readInstance() throws IOException {
-        long start = in.position();
-        long id = readID();
-        StackTrace stackTrace = getStackTraceFromSerial(in.readInt());
-        long classID = readID();
-        int bytesFollowing = in.readInt();
-        int bytesRead = (2 * identifierSize) + 8 + bytesFollowing;
-        JavaObject jobj = new JavaObject(classID, start);
-        skipBytes(bytesFollowing);
-        snapshot.addHeapObject(id, jobj);
-        snapshot.setSiteTrace(jobj, stackTrace);
-        return bytesRead;
-    }
-
-    //
-    // Handle a HPROF_GC_OBJ_ARRAY_DUMP or HPROF_GC_PRIM_ARRAY_DUMP
-    // Return number of bytes read
-    //
-    private int readArray(boolean isPrimitive) throws IOException {
-        long start = in.position();
-        long id = readID();
-        StackTrace stackTrace = getStackTraceFromSerial(in.readInt());
-        int num = in.readInt();
-        int bytesRead = identifierSize + 8;
-        long elementClassID;
-        if (isPrimitive) {
-            elementClassID = in.readByte();
-            bytesRead++;
-        } else {
-            elementClassID = readID();
-            bytesRead += identifierSize;
-        }
-
-        // Check for primitive arrays:
-        byte primitiveSignature = 0x00;
-        int elSize = 0;
-        if (isPrimitive || version < VERSION_JDK12BETA4) {
-            switch ((int)elementClassID) {
-                case T_BOOLEAN: {
-                    primitiveSignature = (byte) 'Z';
-                    elSize = 1;
-                    break;
-                }
-                case T_CHAR: {
-                    primitiveSignature = (byte) 'C';
-                    elSize = 2;
-                    break;
-                }
-                case T_FLOAT: {
-                    primitiveSignature = (byte) 'F';
-                    elSize = 4;
-                    break;
-                }
-                case T_DOUBLE: {
-                    primitiveSignature = (byte) 'D';
-                    elSize = 8;
-                    break;
-                }
-                case T_BYTE: {
-                    primitiveSignature = (byte) 'B';
-                    elSize = 1;
-                    break;
-                }
-                case T_SHORT: {
-                    primitiveSignature = (byte) 'S';
-                    elSize = 2;
-                    break;
-                }
-                case T_INT: {
-                    primitiveSignature = (byte) 'I';
-                    elSize = 4;
-                    break;
-                }
-                case T_LONG: {
-                    primitiveSignature = (byte) 'J';
-                    elSize = 8;
-                    break;
-                }
-            }
-            if (version >= VERSION_JDK12BETA4 && primitiveSignature == 0x00) {
-                throw new IOException("Unrecognized typecode:  "
-                                        + elementClassID);
-            }
-        }
-        if (primitiveSignature != 0x00) {
-            int size = elSize * num;
-            bytesRead += size;
-            JavaValueArray va = new JavaValueArray(primitiveSignature, start);
-            skipBytes(size);
-            snapshot.addHeapObject(id, va);
-            snapshot.setSiteTrace(va, stackTrace);
-        } else {
-            int sz = num * identifierSize;
-            bytesRead += sz;
-            JavaObjectArray arr = new JavaObjectArray(elementClassID, start);
-            skipBytes(sz);
-            snapshot.addHeapObject(id, arr);
-            snapshot.setSiteTrace(arr, stackTrace);
-        }
-        return bytesRead;
-    }
-
-    private byte signatureFromTypeId(byte typeId) throws IOException {
-        switch (typeId) {
-            case T_CLASS: {
-                return (byte) 'L';
-            }
-            case T_BOOLEAN: {
-                return (byte) 'Z';
-            }
-            case T_CHAR: {
-                return (byte) 'C';
-            }
-            case T_FLOAT: {
-                return (byte) 'F';
-            }
-            case T_DOUBLE: {
-                return (byte) 'D';
-            }
-            case T_BYTE: {
-                return (byte) 'B';
-            }
-            case T_SHORT: {
-                return (byte) 'S';
-            }
-            case T_INT: {
-                return (byte) 'I';
-            }
-            case T_LONG: {
-                return (byte) 'J';
-            }
-            default: {
-                throw new IOException("Invalid type id of " + typeId);
-            }
-        }
-    }
-
-    private void handleEOF(EOFException exp, Snapshot snapshot) {
-        if (debugLevel > 0) {
-            exp.printStackTrace();
-        }
-        warn("Unexpected EOF. Will miss information...");
-        // we have EOF, we have to tolerate missing references
-        snapshot.setUnresolvedObjectsOK(true);
-    }
-
-    private void warn(String msg) {
-        System.out.println("WARNING: " + msg);
-    }
-
-    //
-    // A trivial data-holder class for HPROF_GC_ROOT_THREAD_OBJ.
-    //
-    private class ThreadObject {
-
-        long threadId;
-        int stackSeq;
-
-        ThreadObject(long threadId, int stackSeq) {
-            this.threadId = threadId;
-            this.stackSeq = stackSeq;
-        }
-    }
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/parser/MappedReadBuffer.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,114 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.parser;
-
-import java.io.IOException;
-import java.io.RandomAccessFile;
-import java.nio.MappedByteBuffer;
-import java.nio.channels.FileChannel;
-
-/**
- * Implementation of ReadBuffer using mapped file buffer
- *
- * @author A. Sundararajan
- */
-class MappedReadBuffer implements ReadBuffer {
-    private MappedByteBuffer buf;
-
-    MappedReadBuffer(MappedByteBuffer buf) {
-        this.buf = buf;
-    }
-
-    // factory method to create correct ReadBuffer for a given file
-    static ReadBuffer create(RandomAccessFile file) throws IOException {
-        FileChannel ch = file.getChannel();
-        long size = ch.size();
-        // if file size is more than 2 GB and when file mapping is
-        // configured (default), use mapped file reader
-        if (canUseFileMap() && (size <= Integer.MAX_VALUE)) {
-            MappedByteBuffer buf;
-            try {
-                buf = ch.map(FileChannel.MapMode.READ_ONLY, 0, size);
-                ch.close();
-                return new MappedReadBuffer(buf);
-            } catch (IOException exp) {
-                exp.printStackTrace();
-                System.err.println("File mapping failed, will use direct read");
-                // fall through
-            }
-        } // else fall through
-        return new FileReadBuffer(file);
-    }
-
-    private static boolean canUseFileMap() {
-        // set jhat.disableFileMap to any value other than "false"
-        // to disable file mapping
-        String prop = System.getProperty("jhat.disableFileMap");
-        return prop == null || prop.equals("false");
-    }
-
-    private void seek(long pos) throws IOException {
-        assert pos <= Integer.MAX_VALUE :  "position overflow";
-        buf.position((int)pos);
-    }
-
-    public synchronized void get(long pos, byte[] res) throws IOException {
-        seek(pos);
-        buf.get(res);
-    }
-
-    public synchronized char getChar(long pos) throws IOException {
-        seek(pos);
-        return buf.getChar();
-    }
-
-    public synchronized byte getByte(long pos) throws IOException {
-        seek(pos);
-        return buf.get();
-    }
-
-    public synchronized short getShort(long pos) throws IOException {
-        seek(pos);
-        return buf.getShort();
-    }
-
-    public synchronized int getInt(long pos) throws IOException {
-        seek(pos);
-        return buf.getInt();
-    }
-
-    public synchronized long getLong(long pos) throws IOException {
-        seek(pos);
-        return buf.getLong();
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/parser/PositionDataInputStream.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,64 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.parser;
-
-import java.io.DataInputStream;
-import java.io.InputStream;
-
-/**
- * A DataInputStream that keeps track of total bytes read
- * (in effect 'position' in stream) so far.
- *
- */
-public class PositionDataInputStream extends DataInputStream {
-    public PositionDataInputStream(InputStream in) {
-        super(in instanceof PositionInputStream?
-              in : new PositionInputStream(in));
-    }
-
-    public boolean markSupported() {
-        return false;
-    }
-
-    public void mark(int readLimit) {
-        throw new UnsupportedOperationException("mark");
-    }
-
-    public void reset() {
-        throw new UnsupportedOperationException("reset");
-    }
-
-    public long position() {
-        return ((PositionInputStream)in).position();
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/parser/PositionInputStream.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,84 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.parser;
-
-import java.io.FilterInputStream;
-import java.io.IOException;
-import java.io.InputStream;
-
-/**
- * InputStream that keeps track of total bytes read (in effect
- * 'position' in stream) from the input stream.
- *
- */
-public class PositionInputStream extends FilterInputStream {
-    private long position = 0L;
-
-    public PositionInputStream(InputStream in) {
-        super(in);
-    }
-
-    public int read() throws IOException {
-        int res = super.read();
-        if (res != -1) position++;
-        return res;
-    }
-
-    public int read(byte[] b, int off, int len) throws IOException {
-        int res = super.read(b, off, len);
-        if (res != -1) position += res;
-        return res;
-    }
-
-    public long skip(long n) throws IOException {
-        long res = super.skip(n);
-        position += res;
-        return res;
-    }
-
-    public boolean markSupported() {
-        return false;
-    }
-
-    public void mark(int readLimit) {
-        throw new UnsupportedOperationException("mark");
-    }
-
-    public void reset() {
-        throw new UnsupportedOperationException("reset");
-    }
-
-    public long position() {
-        return position;
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/parser/ReadBuffer.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,51 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.parser;
-
-import java.io.IOException;
-
-/**
- * Positionable read only buffer
- *
- * @author A. Sundararajan
- */
-public interface ReadBuffer {
-    // read methods - only byte array and int primitive types.
-    // read position has to be specified always.
-    public void  get(long pos, byte[] buf) throws IOException;
-    public char  getChar(long pos) throws IOException;
-    public byte  getByte(long pos) throws IOException;
-    public short getShort(long pos) throws IOException;
-    public int   getInt(long pos) throws IOException;
-    public long  getLong(long pos) throws IOException;
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/parser/Reader.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,100 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.parser;
-
-import java.io.*;
-import com.sun.tools.hat.internal.model.*;
-
-/**
- * Abstract base class for reading object dump files.  A reader need not be
- * thread-safe.
- *
- * @author      Bill Foote
- */
-
-
-public abstract class Reader {
-    protected PositionDataInputStream in;
-
-    protected Reader(PositionDataInputStream in) {
-        this.in = in;
-    }
-
-    /**
-     * Read a snapshot from a data input stream.  It is assumed that the magic
-     * number has already been read.
-     */
-    abstract public Snapshot read() throws IOException;
-
-    /**
-     * Read a snapshot from a file.
-     *
-     * @param heapFile The name of a file containing a heap dump
-     * @param callStack If true, read the call stack of allocaation sites
-     */
-    public static Snapshot readFile(String heapFile, boolean callStack,
-                                    int debugLevel)
-            throws IOException {
-        int dumpNumber = 1;
-        int pos = heapFile.lastIndexOf('#');
-        if (pos > -1) {
-            String num = heapFile.substring(pos+1, heapFile.length());
-            try {
-                dumpNumber = Integer.parseInt(num, 10);
-            } catch (java.lang.NumberFormatException ex) {
-                String msg = "In file name \"" + heapFile
-                             + "\", a dump number was "
-                             + "expected after the :, but \""
-                             + num + "\" was found instead.";
-                System.err.println(msg);
-                throw new IOException(msg);
-            }
-            heapFile = heapFile.substring(0, pos);
-        }
-        PositionDataInputStream in = new PositionDataInputStream(
-            new BufferedInputStream(new FileInputStream(heapFile)));
-        try {
-            int i = in.readInt();
-            if (i == HprofReader.MAGIC_NUMBER) {
-                Reader r
-                    = new HprofReader(heapFile, in, dumpNumber,
-                                      callStack, debugLevel);
-                return r.read();
-            } else {
-                throw new IOException("Unrecognized magic number: " + i);
-            }
-        } finally {
-            in.close();
-        }
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/AllClassesQuery.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,150 +0,0 @@
-/*
- * Copyright (c) 1997, 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.server;
-
-import com.sun.tools.hat.internal.model.*;
-import java.util.Iterator;
-
-/**
- *
- * @author      Bill Foote
- */
-
-
-class AllClassesQuery extends QueryHandler {
-
-    boolean excludePlatform;
-    boolean oqlSupported;
-
-    public AllClassesQuery(boolean excludePlatform, boolean oqlSupported) {
-        this.excludePlatform = excludePlatform;
-        this.oqlSupported = oqlSupported;
-    }
-
-    public void run() {
-        if (excludePlatform) {
-            startHtml("All Classes (excluding platform)");
-        } else {
-            startHtml("All Classes (including platform)");
-        }
-
-        Iterator<JavaClass> classes = snapshot.getClasses();
-        String lastPackage = null;
-        while (classes.hasNext()) {
-            JavaClass clazz = classes.next();
-            if (excludePlatform && PlatformClasses.isPlatformClass(clazz)) {
-                // skip this..
-                continue;
-            }
-            String name = clazz.getName();
-            int pos = name.lastIndexOf('.');
-            String pkg;
-            if (name.startsWith("[")) {         // Only in ancient heap dumps
-                pkg = "<Arrays>";
-            } else if (pos == -1) {
-                pkg = "<Default Package>";
-            } else {
-                pkg = name.substring(0, pos);
-            }
-            if (!pkg.equals(lastPackage)) {
-                out.print("<h2>Package ");
-                print(pkg);
-                out.println("</h2>");
-            }
-            lastPackage = pkg;
-            printClass(clazz);
-            if (clazz.getId() != -1) {
-                print(" [" + clazz.getIdString() + "]");
-            }
-            out.println("<br>");
-        }
-
-        out.println("<h2>Other Queries</h2>");
-        out.println("<ul>");
-
-        out.println("<li>");
-        printAnchorStart();
-        if (excludePlatform) {
-            out.print("allClassesWithPlatform/\">");
-            print("All classes including platform");
-        } else {
-            out.print("\">");
-            print("All classes excluding platform");
-        }
-        out.println("</a>");
-
-        out.println("<li>");
-        printAnchorStart();
-        out.print("showRoots/\">");
-        print("Show all members of the rootset");
-        out.println("</a>");
-
-        out.println("<li>");
-        printAnchorStart();
-        out.print("showInstanceCounts/includePlatform/\">");
-        print("Show instance counts for all classes (including platform)");
-        out.println("</a>");
-
-        out.println("<li>");
-        printAnchorStart();
-        out.print("showInstanceCounts/\">");
-        print("Show instance counts for all classes (excluding platform)");
-        out.println("</a>");
-
-        out.println("<li>");
-        printAnchorStart();
-        out.print("histo/\">");
-        print("Show heap histogram");
-        out.println("</a>");
-
-        out.println("<li>");
-        printAnchorStart();
-        out.print("finalizerSummary/\">");
-        print("Show finalizer summary");
-        out.println("</a>");
-
-        if (oqlSupported) {
-            out.println("<li>");
-            printAnchorStart();
-            out.print("oql/\">");
-            print("Execute Object Query Language (OQL) query");
-            out.println("</a>");
-        }
-
-        out.println("</ul>");
-
-        endHtml();
-    }
-
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/AllRootsQuery.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,108 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.server;
-
-import java.util.Vector;
-
-import com.sun.tools.hat.internal.model.*;
-import com.sun.tools.hat.internal.util.ArraySorter;
-import com.sun.tools.hat.internal.util.Comparer;
-
-/**
- *
- * @author      Bill Foote
- */
-
-
-class AllRootsQuery extends QueryHandler {
-
-    public AllRootsQuery() {
-    }
-
-    public void run() {
-        startHtml("All Members of the Rootset");
-
-        Root[] roots = snapshot.getRootsArray();
-        ArraySorter.sort(roots, new Comparer() {
-            public int compare(Object lhs, Object rhs) {
-                Root left = (Root) lhs;
-                Root right = (Root) rhs;
-                int d = left.getType() - right.getType();
-                if (d != 0) {
-                    return -d;  // More interesting values are *higher*
-                }
-                return left.getDescription().compareTo(right.getDescription());
-            }
-        });
-
-        int lastType = Root.INVALID_TYPE;
-
-        for (int i= 0; i < roots.length; i++) {
-            Root root = roots[i];
-
-            if (root.getType() != lastType) {
-                lastType = root.getType();
-                out.print("<h2>");
-                print(root.getTypeName() + " References");
-                out.println("</h2>");
-            }
-
-            printRoot(root);
-            if (root.getReferer() != null) {
-                out.print("<small> (from ");
-                printThingAnchorTag(root.getReferer().getId());
-                print(root.getReferer().toString());
-                out.print(")</a></small>");
-            }
-            out.print(" :<br>");
-
-            JavaThing t = snapshot.findThing(root.getId());
-            if (t != null) {    // It should always be
-                print("--> ");
-                printThing(t);
-                out.println("<br>");
-            }
-        }
-
-        out.println("<h2>Other Queries</h2>");
-        out.println("<ul>");
-        out.println("<li>");
-        printAnchorStart();
-        out.print("\">");
-        print("Show All Classes");
-        out.println("</a>");
-        out.println("</ul>");
-
-        endHtml();
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/ClassQuery.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,190 +0,0 @@
-/*
- * Copyright (c) 1997, 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.server;
-
-import com.sun.tools.hat.internal.model.*;
-import com.sun.tools.hat.internal.util.ArraySorter;
-import com.sun.tools.hat.internal.util.Comparer;
-
-import java.util.Enumeration;
-
-/**
- *
- * @author      Bill Foote
- */
-
-
-class ClassQuery extends QueryHandler {
-
-
-    public ClassQuery() {
-    }
-
-    public void run() {
-        startHtml("Class " + query);
-        JavaClass clazz = snapshot.findClass(query);
-        if (clazz == null) {
-            error("class not found: " + query);
-        } else {
-            printFullClass(clazz);
-        }
-        endHtml();
-    }
-
-    protected void printFullClass(JavaClass clazz) {
-        out.print("<h1>");
-        print(clazz.toString());
-        out.println("</h1>");
-
-        out.println("<h2>Superclass:</h2>");
-        printClass(clazz.getSuperclass());
-
-        out.println("<h2>Loader Details</h2>");
-        out.println("<h3>ClassLoader:</h3>");
-        printThing(clazz.getLoader());
-
-        out.println("<h3>Signers:</h3>");
-        printThing(clazz.getSigners());
-
-        out.println("<h3>Protection Domain:</h3>");
-        printThing(clazz.getProtectionDomain());
-
-        out.println("<h2>Subclasses:</h2>");
-        JavaClass[] sc = clazz.getSubclasses();
-        for (int i = 0; i < sc.length; i++) {
-            out.print("    ");
-            printClass(sc[i]);
-            out.println("<br>");
-        }
-
-        out.println("<h2>Instance Data Members:</h2>");
-        JavaField[] ff = clazz.getFields().clone();
-        ArraySorter.sort(ff, new Comparer() {
-            public int compare(Object lhs, Object rhs) {
-                JavaField left = (JavaField) lhs;
-                JavaField right = (JavaField) rhs;
-                return left.getName().compareTo(right.getName());
-            }
-        });
-        for (int i = 0; i < ff.length; i++) {
-            out.print("    ");
-            printField(ff[i]);
-            out.println("<br>");
-        }
-
-        out.println("<h2>Static Data Members:</h2>");
-        JavaStatic[] ss = clazz.getStatics();
-        for (int i = 0; i < ss.length; i++) {
-            printStatic(ss[i]);
-            out.println("<br>");
-        }
-
-        out.println("<h2>Instances</h2>");
-
-        printAnchorStart();
-        print("instances/" + encodeForURL(clazz));
-        out.print("\">");
-        out.println("Exclude subclasses</a><br>");
-
-        printAnchorStart();
-        print("allInstances/" + encodeForURL(clazz));
-        out.print("\">");
-        out.println("Include subclasses</a><br>");
-
-
-        if (snapshot.getHasNewSet()) {
-            out.println("<h2>New Instances</h2>");
-
-            printAnchorStart();
-            print("newInstances/" + encodeForURL(clazz));
-            out.print("\">");
-            out.println("Exclude subclasses</a><br>");
-
-            printAnchorStart();
-            print("allNewInstances/" + encodeForURL(clazz));
-            out.print("\">");
-            out.println("Include subclasses</a><br>");
-        }
-
-        out.println("<h2>References summary by Type</h2>");
-        printAnchorStart();
-        print("refsByType/" + encodeForURL(clazz));
-        out.print("\">");
-        out.println("References summary by type</a>");
-
-        printReferencesTo(clazz);
-    }
-
-    protected void printReferencesTo(JavaHeapObject obj) {
-        if (obj.getId() == -1) {
-            return;
-        }
-        out.println("<h2>References to this object:</h2>");
-        out.flush();
-        Enumeration<JavaThing> referers = obj.getReferers();
-        while (referers.hasMoreElements()) {
-            JavaHeapObject ref = (JavaHeapObject) referers.nextElement();
-            printThing(ref);
-            print (" : " + ref.describeReferenceTo(obj, snapshot));
-            // If there are more than one references, this only gets the
-            // first one.
-            out.println("<br>");
-        }
-
-        out.println("<h2>Other Queries</h2>");
-        out.println("Reference Chains from Rootset");
-        long id = obj.getId();
-
-        out.print("<ul><li>");
-        printAnchorStart();
-        out.print("roots/");
-        printHex(id);
-        out.print("\">");
-        out.println("Exclude weak refs</a>");
-
-        out.print("<li>");
-        printAnchorStart();
-        out.print("allRoots/");
-        printHex(id);
-        out.print("\">");
-        out.println("Include weak refs</a></ul>");
-
-        printAnchorStart();
-        out.print("reachableFrom/");
-        printHex(id);
-        out.print("\">");
-        out.println("Objects reachable from here</a><br>");
-    }
-
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/FinalizerObjectsQuery.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,54 +0,0 @@
-/*
- * Copyright (c) 1997, 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.server;
-
-import com.sun.tools.hat.internal.model.*;
-import java.util.*;
-
-public class FinalizerObjectsQuery extends QueryHandler {
-    public void run() {
-        Enumeration<?> objs = snapshot.getFinalizerObjects();
-        startHtml("Objects pending finalization");
-
-        out.println("<a href='/finalizerSummary/'>Finalizer summary</a>");
-
-        out.println("<h1>Objects pending finalization</h1>");
-
-        while (objs.hasMoreElements()) {
-            printThing((JavaHeapObject)objs.nextElement());
-            out.println("<br>");
-        }
-
-        endHtml();
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/FinalizerSummaryQuery.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,128 +0,0 @@
-/*
- * Copyright (c) 1997, 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.server;
-
-import com.sun.tools.hat.internal.model.*;
-import java.util.*;
-
-public class FinalizerSummaryQuery extends QueryHandler {
-    public void run() {
-        Enumeration<?> objs = snapshot.getFinalizerObjects();
-        startHtml("Finalizer Summary");
-
-        out.println("<p align='center'>");
-        out.println("<b><a href='/'>All Classes (excluding platform)</a></b>");
-        out.println("</p>");
-
-        printFinalizerSummary(objs);
-        endHtml();
-    }
-
-    private static class HistogramElement {
-        public HistogramElement(JavaClass clazz) {
-            this.clazz = clazz;
-        }
-
-        public void updateCount() {
-            this.count++;
-        }
-
-        public int compare(HistogramElement other) {
-            long diff = other.count - count;
-            return (diff == 0L)? 0 : ((diff > 0L)? +1 : -1);
-        }
-
-        public JavaClass getClazz() {
-            return clazz;
-        }
-
-        public long getCount() {
-            return count;
-        }
-
-        private JavaClass clazz;
-        private long count;
-    }
-
-    private void printFinalizerSummary(Enumeration<?> objs) {
-        int count = 0;
-        Map<JavaClass, HistogramElement> map = new HashMap<JavaClass, HistogramElement>();
-
-        while (objs.hasMoreElements()) {
-            JavaHeapObject obj = (JavaHeapObject) objs.nextElement();
-            count++;
-            JavaClass clazz = obj.getClazz();
-            if (! map.containsKey(clazz)) {
-                map.put(clazz, new HistogramElement(clazz));
-            }
-            HistogramElement element = map.get(clazz);
-            element.updateCount();
-        }
-
-        out.println("<p align='center'>");
-        out.println("<b>");
-        out.println("Total ");
-        if (count != 0) {
-            out.print("<a href='/finalizerObjects/'>instances</a>");
-        } else {
-            out.print("instances");
-        }
-        out.println(" pending finalization: ");
-        out.print(count);
-        out.println("</b></p><hr>");
-
-        if (count == 0) {
-            return;
-        }
-
-        // calculate and print histogram
-        HistogramElement[] elements = new HistogramElement[map.size()];
-        map.values().toArray(elements);
-        Arrays.sort(elements, new Comparator<HistogramElement>() {
-                    public int compare(HistogramElement o1, HistogramElement o2) {
-                        return o1.compare(o2);
-                    }
-                });
-
-        out.println("<table border=1 align=center>");
-        out.println("<tr><th>Count</th><th>Class</th></tr>");
-        for (int j = 0; j < elements.length; j++) {
-            out.println("<tr><td>");
-            out.println(elements[j].getCount());
-            out.println("</td><td>");
-            printClass(elements[j].getClazz());
-            out.println("</td><tr>");
-        }
-        out.println("</table>");
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/HistogramQuery.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,99 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.server;
-
-import com.sun.tools.hat.internal.model.JavaClass;
-import java.util.Arrays;
-import java.util.Comparator;
-
-/**
- * Prints histogram sortable by class name, count and size.
- *
- */
-public class HistogramQuery extends QueryHandler {
-    public void run() {
-        JavaClass[] classes = snapshot.getClassesArray();
-        Comparator<JavaClass> comparator;
-        if (query.equals("count")) {
-            comparator = new Comparator<JavaClass>() {
-                public int compare(JavaClass first, JavaClass second) {
-                    long diff = (second.getInstancesCount(false) -
-                             first.getInstancesCount(false));
-                    return (diff == 0)? 0: ((diff < 0)? -1 : + 1);
-                }
-            };
-        } else if (query.equals("class")) {
-            comparator = new Comparator<JavaClass>() {
-                public int compare(JavaClass first, JavaClass second) {
-                    return first.getName().compareTo(second.getName());
-                }
-            };
-        } else {
-            // default sort is by total size
-            comparator = new Comparator<JavaClass>() {
-                public int compare(JavaClass first, JavaClass second) {
-                    long diff = (second.getTotalInstanceSize() -
-                             first.getTotalInstanceSize());
-                    return (diff == 0)? 0: ((diff < 0)? -1 : + 1);
-                }
-            };
-        }
-        Arrays.sort(classes, comparator);
-
-        startHtml("Heap Histogram");
-
-        out.println("<p align='center'>");
-        out.println("<b><a href='/'>All Classes (excluding platform)</a></b>");
-        out.println("</p>");
-
-        out.println("<table align=center border=1>");
-        out.println("<tr><th><a href='/histo/class'>Class</a></th>");
-        out.println("<th><a href='/histo/count'>Instance Count</a></th>");
-        out.println("<th><a href='/histo/size'>Total Size</a></th></tr>");
-        for (int i = 0; i < classes.length; i++) {
-            JavaClass clazz = classes[i];
-            out.println("<tr><td>");
-            printClass(clazz);
-            out.println("</td>");
-            out.println("<td>");
-            out.println(clazz.getInstancesCount(false));
-            out.println("</td>");
-            out.println("<td>");
-            out.println(clazz.getTotalInstanceSize());
-            out.println("</td></tr>");
-        }
-        out.println("</table>");
-
-        endHtml();
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/HttpReader.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,220 +0,0 @@
-/*
- * Copyright (c) 1997, 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.server;
-
-/**
- * Reads a single HTTP query from a socket, and starts up a QueryHandler
- * to server it.
- *
- * @author      Bill Foote
- */
-
-
-import java.net.Socket;
-
-import java.io.InputStream;
-import java.io.BufferedInputStream;
-import java.io.IOException;
-import java.io.BufferedWriter;
-import java.io.PrintWriter;
-import java.io.OutputStreamWriter;
-
-import com.sun.tools.hat.internal.model.Snapshot;
-import com.sun.tools.hat.internal.oql.OQLEngine;
-import com.sun.tools.hat.internal.util.Misc;
-
-public class HttpReader implements Runnable {
-
-
-    private Socket socket;
-    private PrintWriter out;
-    private Snapshot snapshot;
-    private OQLEngine engine;
-
-    public HttpReader (Socket s, Snapshot snapshot, OQLEngine engine) {
-        this.socket = s;
-        this.snapshot = snapshot;
-        this.engine = engine;
-    }
-
-    public void run() {
-        InputStream in = null;
-        try {
-            in = new BufferedInputStream(socket.getInputStream());
-            out = new PrintWriter(new BufferedWriter(
-                            new OutputStreamWriter(
-                                socket.getOutputStream())));
-            out.println("HTTP/1.0 200 OK");
-            out.println("Cache-Control: no-cache");
-            out.println("Pragma: no-cache");
-            out.println();
-            if (in.read() != 'G' || in.read() != 'E'
-                    || in.read() != 'T' || in.read() != ' ') {
-                outputError("Protocol error");
-            }
-            int data;
-            StringBuilder queryBuf = new StringBuilder();
-            while ((data = in.read()) != -1 && data != ' ') {
-                char ch = (char) data;
-                queryBuf.append(ch);
-            }
-            String query = queryBuf.toString();
-            query = java.net.URLDecoder.decode(query, "UTF-8");
-            QueryHandler handler = null;
-            if (snapshot == null) {
-                outputError("The heap snapshot is still being read.");
-                return;
-            } else if (query.equals("/")) {
-                handler = new AllClassesQuery(true, engine != null);
-                handler.setUrlStart("");
-                handler.setQuery("");
-            } else if (query.startsWith("/oql/")) {
-                if (engine != null) {
-                    handler = new OQLQuery(engine);
-                    handler.setUrlStart("");
-                    handler.setQuery(query.substring(5));
-                }
-            } else if (query.startsWith("/oqlhelp/")) {
-                if (engine != null) {
-                    handler = new OQLHelp();
-                    handler.setUrlStart("");
-                    handler.setQuery("");
-                }
-            } else if (query.equals("/allClassesWithPlatform/")) {
-                handler = new AllClassesQuery(false, engine != null);
-                handler.setUrlStart("../");
-                handler.setQuery("");
-            } else if (query.equals("/showRoots/")) {
-                handler = new AllRootsQuery();
-                handler.setUrlStart("../");
-                handler.setQuery("");
-            } else if (query.equals("/showInstanceCounts/includePlatform/")) {
-                handler = new InstancesCountQuery(false);
-                handler.setUrlStart("../../");
-                handler.setQuery("");
-            } else if (query.equals("/showInstanceCounts/")) {
-                handler = new InstancesCountQuery(true);
-                handler.setUrlStart("../");
-                handler.setQuery("");
-            } else if (query.startsWith("/instances/")) {
-                handler = new InstancesQuery(false);
-                handler.setUrlStart("../");
-                handler.setQuery(query.substring(11));
-            }  else if (query.startsWith("/newInstances/")) {
-                handler = new InstancesQuery(false, true);
-                handler.setUrlStart("../");
-                handler.setQuery(query.substring(14));
-            }  else if (query.startsWith("/allInstances/")) {
-                handler = new InstancesQuery(true);
-                handler.setUrlStart("../");
-                handler.setQuery(query.substring(14));
-            }  else if (query.startsWith("/allNewInstances/")) {
-                handler = new InstancesQuery(true, true);
-                handler.setUrlStart("../");
-                handler.setQuery(query.substring(17));
-            } else if (query.startsWith("/object/")) {
-                handler = new ObjectQuery();
-                handler.setUrlStart("../");
-                handler.setQuery(query.substring(8));
-            } else if (query.startsWith("/class/")) {
-                handler = new ClassQuery();
-                handler.setUrlStart("../");
-                handler.setQuery(query.substring(7));
-            } else if (query.startsWith("/roots/")) {
-                handler = new RootsQuery(false);
-                handler.setUrlStart("../");
-                handler.setQuery(query.substring(7));
-            } else if (query.startsWith("/allRoots/")) {
-                handler = new RootsQuery(true);
-                handler.setUrlStart("../");
-                handler.setQuery(query.substring(10));
-            } else if (query.startsWith("/reachableFrom/")) {
-                handler = new ReachableQuery();
-                handler.setUrlStart("../");
-                handler.setQuery(query.substring(15));
-            } else if (query.startsWith("/rootStack/")) {
-                handler = new RootStackQuery();
-                handler.setUrlStart("../");
-                handler.setQuery(query.substring(11));
-            } else if (query.startsWith("/histo/")) {
-                handler = new HistogramQuery();
-                handler.setUrlStart("../");
-                handler.setQuery(query.substring(7));
-            } else if (query.startsWith("/refsByType/")) {
-                handler = new RefsByTypeQuery();
-                handler.setUrlStart("../");
-                handler.setQuery(query.substring(12));
-            } else if (query.startsWith("/finalizerSummary/")) {
-                handler = new FinalizerSummaryQuery();
-                handler.setUrlStart("../");
-                handler.setQuery("");
-            } else if (query.startsWith("/finalizerObjects/")) {
-                handler = new FinalizerObjectsQuery();
-                handler.setUrlStart("../");
-                handler.setQuery("");
-            }
-
-            if (handler != null) {
-                handler.setOutput(out);
-                handler.setSnapshot(snapshot);
-                handler.run();
-            } else {
-                outputError("Query '" + query + "' not implemented");
-            }
-        } catch (IOException ex) {
-            ex.printStackTrace();
-        } finally {
-            if (out != null) {
-                out.close();
-            }
-            try {
-                if (in != null) {
-                    in.close();
-                }
-            } catch (IOException ignored) {
-            }
-            try {
-                socket.close();
-            } catch (IOException ignored) {
-            }
-        }
-    }
-
-    private void outputError(String msg) {
-        out.println();
-        out.println("<html><body bgcolor=\"#ffffff\">");
-        out.println(Misc.encodeHtml(msg));
-        out.println("</body></html>");
-    }
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/InstancesCountQuery.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,169 +0,0 @@
-/*
- * Copyright (c) 1997, 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.server;
-
-import com.sun.tools.hat.internal.model.*;
-import com.sun.tools.hat.internal.util.ArraySorter;
-import com.sun.tools.hat.internal.util.Comparer;
-import java.util.Enumeration;
-
-/**
- *
- * @author      Bill Foote
- */
-
-
-class InstancesCountQuery extends QueryHandler {
-
-
-    private boolean excludePlatform;
-
-    public InstancesCountQuery(boolean excludePlatform) {
-        this.excludePlatform = excludePlatform;
-    }
-
-    public void run() {
-        if (excludePlatform) {
-            startHtml("Instance Counts for All Classes (excluding platform)");
-        } else {
-            startHtml("Instance Counts for All Classes (including platform)");
-        }
-
-        JavaClass[] classes = snapshot.getClassesArray();
-        if (excludePlatform) {
-            int num = 0;
-            for (int i = 0; i < classes.length; i++) {
-                if (! PlatformClasses.isPlatformClass(classes[i])) {
-                    classes[num++] = classes[i];
-                }
-            }
-            JavaClass[] tmp = new JavaClass[num];
-            System.arraycopy(classes, 0, tmp, 0, tmp.length);
-            classes = tmp;
-        }
-        ArraySorter.sort(classes, new Comparer() {
-            public int compare(Object lhso, Object rhso) {
-                JavaClass lhs = (JavaClass) lhso;
-                JavaClass rhs = (JavaClass) rhso;
-                int diff = lhs.getInstancesCount(false)
-                                - rhs.getInstancesCount(false);
-                if (diff != 0) {
-                    return -diff;       // Sort from biggest to smallest
-                }
-                String left = lhs.getName();
-                String right = rhs.getName();
-                if (left.startsWith("[") != right.startsWith("[")) {
-                    // Arrays at the end
-                    if (left.startsWith("[")) {
-                        return 1;
-                    } else {
-                        return -1;
-                    }
-                }
-                return left.compareTo(right);
-            }
-        });
-
-        String lastPackage = null;
-        long totalSize = 0;
-        long instances = 0;
-        for (int i = 0; i < classes.length; i++) {
-            JavaClass clazz = classes[i];
-            int count = clazz.getInstancesCount(false);
-            print("" + count);
-            printAnchorStart();
-            print("instances/" + encodeForURL(classes[i]));
-            out.print("\"> ");
-            if (count == 1) {
-                print("instance");
-            } else {
-                print("instances");
-            }
-            out.print("</a> ");
-            if (snapshot.getHasNewSet()) {
-                Enumeration<JavaHeapObject> objects = clazz.getInstances(false);
-                int newInst = 0;
-                while (objects.hasMoreElements()) {
-                    JavaHeapObject obj = objects.nextElement();
-                    if (obj.isNew()) {
-                        newInst++;
-                    }
-                }
-                print("(");
-                printAnchorStart();
-                print("newInstances/" + encodeForURL(classes[i]));
-                out.print("\">");
-                print("" + newInst + " new");
-                out.print("</a>) ");
-            }
-            print("of ");
-            printClass(classes[i]);
-            out.println("<br>");
-            instances += count;
-            totalSize += classes[i].getTotalInstanceSize();
-        }
-        out.println("<h2>Total of " + instances + " instances occupying " + totalSize + " bytes.</h2>");
-
-        out.println("<h2>Other Queries</h2>");
-        out.println("<ul>");
-
-        out.print("<li>");
-        printAnchorStart();
-        if (!excludePlatform) {
-            out.print("showInstanceCounts/\">");
-            print("Show instance counts for all classes (excluding platform)");
-        } else {
-            out.print("showInstanceCounts/includePlatform/\">");
-            print("Show instance counts for all classes (including platform)");
-        }
-        out.println("</a>");
-
-        out.print("<li>");
-        printAnchorStart();
-        out.print("allClassesWithPlatform/\">");
-        print("Show All Classes (including platform)");
-        out.println("</a>");
-
-        out.print("<li>");
-        printAnchorStart();
-        out.print("\">");
-        print("Show All Classes (excluding platform)");
-        out.println("</a>");
-
-        out.println("</ul>");
-
-        endHtml();
-    }
-
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/InstancesQuery.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,92 +0,0 @@
-/*
- * Copyright (c) 1997, 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.server;
-
-import com.sun.tools.hat.internal.model.*;
-import java.util.Enumeration;
-
-/**
- *
- * @author      Bill Foote
- */
-
-
-class InstancesQuery extends QueryHandler {
-
-    private boolean includeSubclasses;
-    private boolean newObjects;
-
-    public InstancesQuery(boolean includeSubclasses) {
-        this.includeSubclasses = includeSubclasses;
-    }
-
-    public InstancesQuery(boolean includeSubclasses, boolean newObjects) {
-        this.includeSubclasses = includeSubclasses;
-        this.newObjects = newObjects;
-    }
-
-    public void run() {
-        JavaClass clazz = snapshot.findClass(query);
-        String instancesOf;
-        if (newObjects)
-            instancesOf = "New instances of ";
-        else
-            instancesOf = "Instances of ";
-        if (includeSubclasses) {
-            startHtml(instancesOf + query + " (including subclasses)");
-        } else {
-            startHtml(instancesOf + query);
-        }
-        if (clazz == null) {
-            error("Class not found");
-        } else {
-            out.print("<strong>");
-            printClass(clazz);
-            out.print("</strong><br><br>");
-            Enumeration<JavaHeapObject> objects = clazz.getInstances(includeSubclasses);
-            long totalSize = 0;
-            long instances = 0;
-            while (objects.hasMoreElements()) {
-                JavaHeapObject obj = objects.nextElement();
-                if (newObjects && !obj.isNew())
-                    continue;
-                printThing(obj);
-                out.println("<br>");
-                totalSize += obj.getSize();
-                instances++;
-            }
-            out.println("<h2>Total of " + instances + " instances occupying " + totalSize + " bytes.</h2>");
-        }
-        endHtml();
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/OQLHelp.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,60 +0,0 @@
-/*
- * Copyright (c) 1997, 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.server;
-
-import java.io.*;
-
-/**
- * This handles Object Query Language (OQL) help.
- *
- * @author A. Sundararajan
- */
-
-class OQLHelp extends QueryHandler {
-
-    public OQLHelp() {
-    }
-
-    public void run() {
-        InputStream is = getClass().getResourceAsStream("/com/sun/tools/hat/resources/oqlhelp.html");
-        int ch = -1;
-        try {
-            is = new BufferedInputStream(is);
-            while ( (ch = is.read()) != -1) {
-                out.print((char)ch);
-            }
-        } catch (Exception exp) {
-            printException(exp);
-        }
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/OQLQuery.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,104 +0,0 @@
-/*
- * Copyright (c) 1997, 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.server;
-
-import com.sun.tools.hat.internal.oql.*;
-
-/**
- * This handles Object Query Language (OQL) queries.
- *
- * @author A. Sundararajan
- */
-
-class OQLQuery extends QueryHandler {
-
-    public OQLQuery(OQLEngine engine) {
-        this.engine = engine;
-    }
-
-    public void run() {
-        startHtml("Object Query Language (OQL) query");
-        String oql = null;
-        if (query != null && !query.equals("")) {
-            int index = query.indexOf("?query=");
-            if (index != -1 && query.length() > 7) {
-                oql = query.substring(index + 7);
-            }
-        }
-        out.println("<p align='center'><table>");
-        out.println("<tr><td><b>");
-        out.println("<a href='/'>All Classes (excluding platform)</a>");
-        out.println("</b></td>");
-        out.println("<td><b><a href='/oqlhelp/'>OQL Help</a></b></td></tr>");
-        out.println("</table></p>");
-        out.println("<form action='/oql/' method='get'>");
-        out.println("<p align='center'>");
-        out.println("<textarea name='query' cols=80 rows=10>");
-        if (oql != null) {
-            println(oql);
-        }
-        out.println("</textarea>");
-        out.println("</p>");
-        out.println("<p align='center'>");
-        out.println("<input type='submit' value='Execute'></input>");
-        out.println("</p>");
-        out.println("</form>");
-        if (oql != null) {
-            executeQuery(oql);
-        }
-        endHtml();
-    }
-
-    private void executeQuery(String q) {
-        try {
-            out.println("<table border='1'>");
-            engine.executeQuery(q, new ObjectVisitor() {
-                     public boolean visit(Object o) {
-                         out.println("<tr><td>");
-                         try {
-                             out.println(engine.toHtml(o));
-                         } catch (Exception e) {
-                             printException(e);
-                         }
-                         out.println("</td></tr>");
-                         return false;
-                     }
-                 });
-            out.println("</table>");
-        } catch (OQLException exp) {
-            printException(exp);
-        }
-    }
-
-    private OQLEngine engine;
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/ObjectQuery.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,146 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.server;
-
-import  java.util.Enumeration;
-
-import com.sun.tools.hat.internal.model.*;
-import com.sun.tools.hat.internal.util.ArraySorter;
-import com.sun.tools.hat.internal.util.Comparer;
-
-/**
- *
- * @author      Bill Foote
- */
-
-
-class ObjectQuery extends ClassQuery {
-        // We inherit printFullClass from ClassQuery
-
-    public ObjectQuery() {
-    }
-
-    public void run() {
-        startHtml("Object at " + query);
-        long id = parseHex(query);
-        JavaHeapObject thing = snapshot.findThing(id);
-        //
-        // In the following, I suppose we really should use a visitor
-        // pattern.  I'm not that strongly motivated to do this, however:
-        // This is the only typecase there is, and the default for an
-        // unrecognized type is to do something reasonable.
-        //
-        if (thing == null) {
-            error("object not found");
-        } else if (thing instanceof JavaClass) {
-            printFullClass((JavaClass) thing);
-        } else if (thing instanceof JavaValueArray) {
-            print(((JavaValueArray) thing).valueString(true));
-            printAllocationSite(thing);
-            printReferencesTo(thing);
-        } else if (thing instanceof JavaObjectArray) {
-            printFullObjectArray((JavaObjectArray) thing);
-            printAllocationSite(thing);
-            printReferencesTo(thing);
-        } else if (thing instanceof JavaObject) {
-            printFullObject((JavaObject) thing);
-            printAllocationSite(thing);
-            printReferencesTo(thing);
-        } else {
-            // We should never get here
-            print(thing.toString());
-            printReferencesTo(thing);
-        }
-        endHtml();
-    }
-
-
-    private void printFullObject(JavaObject obj) {
-        out.print("<h1>instance of ");
-        print(obj.toString());
-        out.print(" <small>(" + obj.getSize() + " bytes)</small>");
-        out.println("</h1>\n");
-
-        out.println("<h2>Class:</h2>");
-        printClass(obj.getClazz());
-
-        out.println("<h2>Instance data members:</h2>");
-        final JavaThing[] things = obj.getFields();
-        final JavaField[] fields = obj.getClazz().getFieldsForInstance();
-        Integer[] hack = new Integer[things.length];
-        for (int i = 0; i < things.length; i++) {
-            hack[i] = i;
-        }
-        ArraySorter.sort(hack, new Comparer() {
-            public int compare(Object lhs, Object rhs) {
-                JavaField left = fields[((Integer) lhs).intValue()];
-                JavaField right = fields[((Integer) rhs).intValue()];
-                return left.getName().compareTo(right.getName());
-            }
-        });
-        for (int i = 0; i < things.length; i++) {
-            int index = hack[i].intValue();
-            printField(fields[index]);
-            out.print(" : ");
-            printThing(things[index]);
-            out.println("<br>");
-        }
-    }
-
-    private void printFullObjectArray(JavaObjectArray arr) {
-        JavaThing[] elements = arr.getElements();
-        out.println("<h1>Array of " + elements.length + " objects</h1>");
-
-        out.println("<h2>Class:</h2>");
-        printClass(arr.getClazz());
-
-        out.println("<h2>Values</h2>");
-        for (int i = 0; i < elements.length; i++) {
-            out.print("" + i + " : ");
-            printThing(elements[i]);
-            out.println("<br>");
-        }
-    }
-
-    //
-    // Print the StackTrace where this was allocated
-    //
-    private void printAllocationSite(JavaHeapObject obj) {
-        StackTrace trace = obj.getAllocatedFrom();
-        if (trace == null || trace.getFrames().length == 0) {
-            return;
-        }
-        out.println("<h2>Object allocated from:</h2>");
-        printStackTrace(trace);
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/PlatformClasses.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,119 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.server;
-
-import com.sun.tools.hat.internal.model.JavaClass;
-import com.sun.tools.hat.internal.model.Snapshot;
-
-import java.util.LinkedList;
-import java.io.InputStream;
-import java.io.Reader;
-import java.io.InputStreamReader;
-import java.io.BufferedReader;
-import java.io.IOException;
-
-/**
- * This class is a helper that determines if a class is a "platform"
- * class or not.  It's a platform class if its name starts with one of
- * the prefixes to be found in /com/sun/tools/hat/resources/platform_names.txt.
- *
- * @author      Bill Foote
- */
-
-public class PlatformClasses  {
-
-    static String[] names = null;
-
-
-    public static synchronized String[] getNames() {
-        if (names == null) {
-            LinkedList<String> list = new LinkedList<String>();
-            InputStream str
-                = PlatformClasses.class
-                    .getResourceAsStream("/com/sun/tools/hat/resources/platform_names.txt");
-            if (str != null) {
-                try {
-                    BufferedReader rdr
-                        = new BufferedReader(new InputStreamReader(str));
-                    for (;;) {
-                        String s = rdr.readLine();
-                        if (s == null) {
-                            break;
-                        } else if (s.length() > 0) {
-                            list.add(s);
-                        }
-                    }
-                    rdr.close();
-                    str.close();
-                } catch (IOException ex) {
-                    ex.printStackTrace();
-                    // Shouldn't happen, and if it does, continuing
-                    // is the right thing to do anyway.
-                }
-            }
-            names = list.toArray(new String[list.size()]);
-        }
-        return names;
-    }
-
-
-    public static boolean isPlatformClass(JavaClass clazz) {
-        // all classes loaded by bootstrap loader are considered
-        // platform classes. In addition, the older name based filtering
-        // is also done for compatibility.
-        if (clazz.isBootstrap()) {
-            return true;
-        }
-
-        String name = clazz.getName();
-        // skip even the array classes of the skipped classes.
-        if (name.startsWith("[")) {
-            int index = name.lastIndexOf('[');
-            if (index != -1) {
-                if (name.charAt(index + 1) != 'L') {
-                    // some primitive array.
-                    return true;
-                }
-                // skip upto 'L' after the last '['.
-                name = name.substring(index + 2);
-            }
-        }
-        String[] nms = getNames();
-        for (int i = 0; i < nms.length; i++) {
-            if (name.startsWith(nms[i])) {
-                return true;
-            }
-        }
-        return false;
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/QueryHandler.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,239 +0,0 @@
-/*
- * Copyright (c) 1997, 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.server;
-
-import java.io.PrintWriter;
-
-import com.sun.tools.hat.internal.model.*;
-import com.sun.tools.hat.internal.util.Misc;
-import java.io.StringWriter;
-
-import java.net.URLEncoder;
-import java.io.UnsupportedEncodingException;
-
-/**
- *
- * @author      Bill Foote
- */
-
-
-abstract class QueryHandler {
-
-    protected String urlStart;
-    protected String query;
-    protected PrintWriter out;
-    protected Snapshot snapshot;
-
-    abstract void run();
-
-
-    void setUrlStart(String s) {
-        urlStart = s;
-    }
-
-    void setQuery(String s) {
-        query = s;
-    }
-
-    void setOutput(PrintWriter o) {
-        this.out = o;
-    }
-
-    void setSnapshot(Snapshot ss) {
-        this.snapshot = ss;
-    }
-
-    protected String encodeForURL(String s) {
-        try {
-            s = URLEncoder.encode(s, "UTF-8");
-        } catch (UnsupportedEncodingException ex) {
-            // Should never happen
-            ex.printStackTrace();
-        }
-        return s;
-    }
-
-    protected void startHtml(String title) {
-        out.print("<html><title>");
-        print(title);
-        out.println("</title>");
-        out.println("<body bgcolor=\"#ffffff\"><center><h1>");
-        print(title);
-        out.println("</h1></center>");
-    }
-
-    protected void endHtml() {
-        out.println("</body></html>");
-    }
-
-    protected void error(String msg) {
-        println(msg);
-    }
-
-    protected void printAnchorStart() {
-        out.print("<a href=\"");
-        out.print(urlStart);
-    }
-
-    protected void printThingAnchorTag(long id) {
-        printAnchorStart();
-        out.print("object/");
-        printHex(id);
-        out.print("\">");
-    }
-
-    protected void printObject(JavaObject obj) {
-        printThing(obj);
-    }
-
-    protected void printThing(JavaThing thing) {
-        if (thing == null) {
-            out.print("null");
-            return;
-        }
-        if (thing instanceof JavaHeapObject) {
-            JavaHeapObject ho = (JavaHeapObject) thing;
-            long id = ho.getId();
-            if (id != -1L) {
-                if (ho.isNew())
-                out.println("<strong>");
-                printThingAnchorTag(id);
-            }
-            print(thing.toString());
-            if (id != -1) {
-                if (ho.isNew())
-                    out.println("[new]</strong>");
-                out.print(" (" + ho.getSize() + " bytes)");
-                out.println("</a>");
-            }
-        } else {
-            print(thing.toString());
-        }
-    }
-
-    protected void printRoot(Root root) {
-        StackTrace st = root.getStackTrace();
-        boolean traceAvailable = (st != null) && (st.getFrames().length != 0);
-        if (traceAvailable) {
-            printAnchorStart();
-            out.print("rootStack/");
-            printHex(root.getIndex());
-            out.print("\">");
-        }
-        print(root.getDescription());
-        if (traceAvailable) {
-            out.print("</a>");
-        }
-    }
-
-    protected void printClass(JavaClass clazz) {
-        if (clazz == null) {
-            out.println("null");
-            return;
-        }
-        printAnchorStart();
-        out.print("class/");
-        print(encodeForURL(clazz));
-        out.print("\">");
-        print(clazz.toString());
-        out.println("</a>");
-    }
-
-    protected String encodeForURL(JavaClass clazz) {
-        if (clazz.getId() == -1) {
-            return encodeForURL(clazz.getName());
-        } else {
-            return clazz.getIdString();
-        }
-    }
-
-    protected void printField(JavaField field) {
-        print(field.getName() + " (" + field.getSignature() + ")");
-    }
-
-    protected void printStatic(JavaStatic member) {
-        JavaField f = member.getField();
-        printField(f);
-        out.print(" : ");
-        if (f.hasId()) {
-            JavaThing t = member.getValue();
-            printThing(t);
-        } else {
-            print(member.getValue().toString());
-        }
-    }
-
-    protected void printStackTrace(StackTrace trace) {
-        StackFrame[] frames = trace.getFrames();
-        for (int i = 0; i < frames.length; i++) {
-            StackFrame f = frames[i];
-            String clazz = f.getClassName();
-            out.print("<font color=purple>");
-            print(clazz);
-            out.print("</font>");
-            print("." + f.getMethodName() + "(" + f.getMethodSignature() + ")");
-            out.print(" <bold>:</bold> ");
-            print(f.getSourceFileName() + " line " + f.getLineNumber());
-            out.println("<br>");
-        }
-    }
-
-    protected void printException(Throwable t) {
-        println(t.getMessage());
-        out.println("<pre>");
-        StringWriter sw = new StringWriter();
-        t.printStackTrace(new PrintWriter(sw));
-        print(sw.toString());
-        out.println("</pre>");
-    }
-
-    protected void printHex(long addr) {
-        if (snapshot.getIdentifierSize() == 4) {
-            out.print(Misc.toHex((int)addr));
-        } else {
-            out.print(Misc.toHex(addr));
-        }
-    }
-
-    protected long parseHex(String value) {
-        return Misc.parseHex(value);
-    }
-
-    protected void print(String str) {
-        out.print(Misc.encodeHtml(str));
-    }
-
-    protected void println(String str) {
-        out.println(Misc.encodeHtml(str));
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/QueryListener.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,111 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.server;
-
-/**
- *
- * @author      Bill Foote
- */
-
-
-import java.net.Socket;
-import java.net.ServerSocket;
-import java.net.InetAddress;
-
-import java.io.InputStream;
-import java.io.BufferedInputStream;
-import java.io.IOException;
-import java.io.Writer;
-import java.io.BufferedWriter;
-import java.io.PrintWriter;
-import java.io.OutputStream;
-import java.io.OutputStreamWriter;
-import java.io.BufferedOutputStream;
-
-import com.sun.tools.hat.internal.model.Snapshot;
-import com.sun.tools.hat.internal.oql.OQLEngine;
-
-public class QueryListener implements Runnable {
-
-
-    private Snapshot snapshot;
-    private OQLEngine engine;
-    private int port;
-
-    public QueryListener(int port) {
-        this.port = port;
-        this.snapshot = null;   // Client will setModel when it's ready
-        this.engine = null; // created when snapshot is set
-    }
-
-    public void setModel(Snapshot ss) {
-        this.snapshot = ss;
-        if (OQLEngine.isOQLSupported()) {
-            this.engine = new OQLEngine(ss);
-        }
-    }
-
-    public void run() {
-        try {
-            waitForRequests();
-        } catch (IOException ex) {
-            ex.printStackTrace();
-            System.exit(1);
-        }
-    }
-
-    private void waitForRequests() throws IOException {
-        ServerSocket ss = new ServerSocket(port);
-        Thread last = null;
-        for (;;) {
-            Socket s = ss.accept();
-            Thread t = new Thread(new HttpReader(s, snapshot, engine));
-            if (snapshot == null) {
-                t.setPriority(Thread.NORM_PRIORITY+1);
-            } else {
-                t.setPriority(Thread.NORM_PRIORITY-1);
-                if (last != null) {
-                    try {
-                        last.setPriority(Thread.NORM_PRIORITY-2);
-                    } catch (Throwable ignored) {
-                    }
-                    // If the thread is no longer alive, we'll get a
-                    // NullPointerException
-                }
-            }
-            t.start();
-            last = t;
-        }
-    }
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/ReachableQuery.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,90 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.server;
-
-import com.sun.tools.hat.internal.model.*;
-
-/**
- *
- * @author      Bill Foote
- */
-
-
-class ReachableQuery extends QueryHandler {
-        // We inherit printFullClass from ClassQuery
-
-
-    public ReachableQuery() {
-    }
-
-    public void run() {
-        startHtml("Objects Reachable From " + query);
-        long id = parseHex(query);
-        JavaHeapObject root = snapshot.findThing(id);
-        ReachableObjects ro = new ReachableObjects(root,
-                                   snapshot.getReachableExcludes());
-        // Now, print out the sorted list, but start with root
-        long totalSize = ro.getTotalSize();
-        JavaThing[] things = ro.getReachables();
-        long instances = things.length;
-
-        out.print("<strong>");
-        printThing(root);
-        out.println("</strong><br>");
-        out.println("<br>");
-        for (int i = 0; i < things.length; i++) {
-            printThing(things[i]);
-            out.println("<br>");
-        }
-
-        printFields(ro.getUsedFields(), "Data Members Followed");
-        printFields(ro.getExcludedFields(), "Excluded Data Members");
-        out.println("<h2>Total of " + instances + " instances occupying " + totalSize + " bytes.</h2>");
-
-        endHtml();
-    }
-
-    private void printFields(String[] fields, String title) {
-        if (fields.length == 0) {
-            return;
-        }
-        out.print("<h3>");
-        print(title);
-        out.println("</h3>");
-
-        for (int i = 0; i < fields.length; i++) {
-            print(fields[i]);
-            out.println("<br>");
-        }
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/RefsByTypeQuery.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,138 +0,0 @@
-/*
- * Copyright (c) 1997, 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.server;
-
-import com.sun.tools.hat.internal.model.*;
-import java.util.*;
-
-/**
- * References by type summary
- *
- */
-public class RefsByTypeQuery extends QueryHandler {
-    public void run() {
-        JavaClass clazz = snapshot.findClass(query);
-        if (clazz == null) {
-            error("class not found: " + query);
-        } else {
-            Map<JavaClass, Long> referrersStat = new HashMap<JavaClass, Long>();
-            final Map<JavaClass, Long> refereesStat = new HashMap<JavaClass, Long>();
-            Enumeration<JavaHeapObject> instances = clazz.getInstances(false);
-            while (instances.hasMoreElements()) {
-                JavaHeapObject instance = instances.nextElement();
-                if (instance.getId() == -1) {
-                    continue;
-                }
-                Enumeration<JavaThing> e = instance.getReferers();
-                while (e.hasMoreElements()) {
-                    JavaHeapObject ref = (JavaHeapObject)e.nextElement();
-                    JavaClass cl = ref.getClazz();
-                    if (cl == null) {
-                         System.out.println("null class for " + ref);
-                         continue;
-                    }
-                    Long count = referrersStat.get(cl);
-                    if (count == null) {
-                        count = 1L;
-                    } else {
-                        count = count + 1L;
-                    }
-                    referrersStat.put(cl, count);
-                }
-                instance.visitReferencedObjects(
-                    new AbstractJavaHeapObjectVisitor() {
-                        public void visit(JavaHeapObject obj) {
-                            JavaClass cl = obj.getClazz();
-                            Long count = refereesStat.get(cl);
-                            if (count == null) {
-                                count = 1L;
-                            } else {
-                                count = count + 1L;
-                            }
-                            refereesStat.put(cl, count);
-                        }
-                    }
-                );
-            } // for each instance
-
-            startHtml("References by Type");
-            out.println("<p align='center'>");
-            printClass(clazz);
-            if (clazz.getId() != -1) {
-                println("[" + clazz.getIdString() + "]");
-            }
-            out.println("</p>");
-
-            if (referrersStat.size() != 0) {
-                out.println("<h3 align='center'>Referrers by Type</h3>");
-                print(referrersStat);
-            }
-
-            if (refereesStat.size() != 0) {
-                out.println("<h3 align='center'>Referees by Type</h3>");
-                print(refereesStat);
-            }
-
-            endHtml();
-        }  // clazz != null
-    } // run
-
-    private void print(final Map<JavaClass, Long> map) {
-        out.println("<table border='1' align='center'>");
-        Set<JavaClass> keys = map.keySet();
-        JavaClass[] classes = new JavaClass[keys.size()];
-        keys.toArray(classes);
-        Arrays.sort(classes, new Comparator<JavaClass>() {
-            public int compare(JavaClass first, JavaClass second) {
-                Long count1 = map.get(first);
-                Long count2 = map.get(second);
-                return count2.compareTo(count1);
-            }
-        });
-
-        out.println("<tr><th>Class</th><th>Count</th></tr>");
-        for (int i = 0; i < classes.length; i++) {
-            JavaClass clazz = classes[i];
-            out.println("<tr><td>");
-            out.print("<a href='/refsByType/");
-            print(clazz.getIdString());
-            out.print("'>");
-            print(clazz.getName());
-            out.println("</a>");
-            out.println("</td><td>");
-            out.println(map.get(clazz));
-            out.println("</td></tr>");
-        }
-        out.println("</table>");
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/RootStackQuery.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,69 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.server;
-
-
-import com.sun.tools.hat.internal.model.*;
-
-/**
- * Query to show the StackTrace for a given root
- *
- * @author      Bill Foote
- */
-
-
-class RootStackQuery extends QueryHandler {
-
-    public RootStackQuery() {
-    }
-
-    public void run() {
-        int index = (int) parseHex(query);
-        Root root = snapshot.getRootAt(index);
-        if (root == null) {
-            error("Root at " + index + " not found");
-            return;
-        }
-        StackTrace st = root.getStackTrace();
-        if (st == null || st.getFrames().length == 0) {
-            error("No stack trace for " + root.getDescription());
-            return;
-        }
-        startHtml("Stack Trace for " + root.getDescription());
-        out.println("<p>");
-        printStackTrace(st);
-        out.println("</p>");
-        endHtml();
-    }
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/server/RootsQuery.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,147 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.server;
-
-import java.util.Vector;
-
-import com.sun.tools.hat.internal.model.*;
-import com.sun.tools.hat.internal.util.ArraySorter;
-import com.sun.tools.hat.internal.util.Comparer;
-
-/**
- *
- * @author      Bill Foote
- */
-
-
-class RootsQuery extends QueryHandler {
-
-    private boolean includeWeak;
-
-    public RootsQuery(boolean includeWeak) {
-        this.includeWeak = includeWeak;
-    }
-
-    public void run() {
-        long id = parseHex(query);
-        JavaHeapObject target = snapshot.findThing(id);
-        if (target == null) {
-            startHtml("Object not found for rootset");
-            error("object not found");
-            endHtml();
-            return;
-        }
-        if (includeWeak) {
-            startHtml("Rootset references to " + target
-                        + " (includes weak refs)");
-        } else {
-            startHtml("Rootset references to " + target
-                        + " (excludes weak refs)");
-        }
-        out.flush();
-
-        ReferenceChain[] refs
-            = snapshot.rootsetReferencesTo(target, includeWeak);
-        ArraySorter.sort(refs, new Comparer() {
-            public int compare(Object lhs, Object rhs) {
-                ReferenceChain left = (ReferenceChain) lhs;
-                ReferenceChain right = (ReferenceChain) rhs;
-                Root leftR = left.getObj().getRoot();
-                Root rightR = right.getObj().getRoot();
-                int d = leftR.getType() - rightR.getType();
-                if (d != 0) {
-                    return -d;  // More interesting values are *higher*
-                }
-                return left.getDepth() - right.getDepth();
-            }
-        });
-
-        out.print("<h1>References to ");
-        printThing(target);
-        out.println("</h1>");
-        int lastType = Root.INVALID_TYPE;
-        for (int i= 0; i < refs.length; i++) {
-            ReferenceChain ref = refs[i];
-            Root root = ref.getObj().getRoot();
-            if (root.getType() != lastType) {
-                lastType = root.getType();
-                out.print("<h2>");
-                print(root.getTypeName() + " References");
-                out.println("</h2>");
-            }
-            out.print("<h3>");
-            printRoot(root);
-            if (root.getReferer() != null) {
-                out.print("<small> (from ");
-                printThingAnchorTag(root.getReferer().getId());
-                print(root.getReferer().toString());
-                out.print(")</a></small>");
-
-            }
-            out.print(" :</h3>");
-            while (ref != null) {
-                ReferenceChain next = ref.getNext();
-                JavaHeapObject obj = ref.getObj();
-                print("--> ");
-                printThing(obj);
-                if (next != null) {
-                    print(" (" +
-                          obj.describeReferenceTo(next.getObj(), snapshot)
-                          + ":)");
-                }
-                out.println("<br>");
-                ref = next;
-            }
-        }
-
-        out.println("<h2>Other queries</h2>");
-
-        if (includeWeak) {
-            printAnchorStart();
-            out.print("roots/");
-            printHex(id);
-            out.print("\">");
-            out.println("Exclude weak refs</a><br>");
-            endHtml();
-        }
-
-        if (!includeWeak) {
-            printAnchorStart();
-            out.print("allRoots/");
-            printHex(id);
-            out.print("\">");
-            out.println("Include weak refs</a><br>");
-        }
-    }
-
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/util/ArraySorter.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,147 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.util;
-import java.util.*;
-
-/**
- * A singleton utility class that sorts an array of objects.
- * <p>
- * Use:
- * <pre>
- *
- *  Stuff[] arr = ...;
- *  ArraySorter.sort(arr, new Comparer() {
- *      public int compare(Object lhs, Object rhs) {
- *          return ((String) lhs).compareTo((String) rhs);
- *      }
- *  });
- * </pre>
- *
- * @author      Bill Foote
- */
-
-public class ArraySorter {
-
-    /**
-     * Sort the given array, using c for comparison
-    **/
-    static public void sort(Object[] arr, Comparer c)  {
-        quickSort(arr, c, 0, arr.length-1);
-    }
-
-
-    /**
-     * Sort an array of strings, using String.compareTo()
-    **/
-    static public void sortArrayOfStrings(Object[] arr) {
-        sort(arr, new Comparer() {
-            public int compare(Object lhs, Object rhs) {
-                return ((String) lhs).compareTo((String) rhs);
-            }
-        });
-    }
-
-
-    static private void swap(Object[] arr, int a, int b) {
-        Object tmp = arr[a];
-        arr[a] = arr[b];
-        arr[b] = tmp;
-    }
-
-    //
-    // Sorts arr between from and to, inclusive.  This is a quick, off-the-top-
-    // of-my-head quicksort:  I haven't put any thought into optimizing it.
-    // I _did_ put thought into making sure it's safe (it will always
-    // terminate).  Worst-case it's O(n^2), but it will usually run in
-    // in O(n log n).  It's well-behaved if the list is already sorted,
-    // or nearly so.
-    //
-    static private void quickSort(Object[] arr, Comparer c, int from, int to) {
-        if (to <= from)
-            return;
-        int mid = (from + to) / 2;
-        if (mid != from)
-            swap(arr, mid, from);
-        Object pivot = arr[from];   // Simple-minded, but reasonable
-        int highestBelowPivot = from - 1;
-        int low = from+1;
-        int high = to;
-            // We now move low and high toward each other, maintaining the
-            // invariants:
-            //      arr[i] <= pivot    for all i < low
-            //      arr[i] > pivot     for all i > high
-            // As long as these invariants hold, and every iteration makes
-            // progress, we are safe.
-        while (low <= high) {
-            int cmp = c.compare(arr[low], pivot);
-            if (cmp <= 0) {   // arr[low] <= pivot
-                if (cmp < 0) {
-                    highestBelowPivot = low;
-                }
-                low++;
-            } else {
-                int c2;
-                for (;;) {
-                        // arr[high] > pivot:
-                    c2 = c.compare(arr[high], pivot);
-                    if (c2 > 0) {
-                        high--;
-                        if (low > high) {
-                            break;
-                        }
-                    } else {
-                        break;
-                    }
-                }
-                // At this point, low is never == high, BTW
-                if (low <= high) {
-                    swap(arr, low, high);
-                    if (c2 < 0) {
-                        highestBelowPivot = low;
-                    }
-                    low++;
-                    high--;
-                }
-            }
-        }
-        // At this point, low == high+1
-        // Now we just need to sort from from..highestBelowPivot
-        // and from high+1..to
-        if (highestBelowPivot > from) {
-            // pivot == pivot, so ensure algorithm terminates
-            swap(arr, from, highestBelowPivot);
-            quickSort(arr, c, from, highestBelowPivot-1);
-        }
-        quickSort(arr, c, high+1, to);
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/util/Comparer.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,49 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.util;
-
-/**
- * Base class for comparison of two objects.
- * @see VectorSorter
- *
- * @author      Bill Foote
- */
-
-abstract public class Comparer {
-
-    /**
-     * @return a number <, == or > 0 depending on lhs compared to rhs
-     * @see java.lang.String.compareTo
-    **/
-    abstract public int compare(Object lhs, Object rhs);
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/util/CompositeEnumeration.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,63 +0,0 @@
-/*
- * Copyright (c) 1997, 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.util;
-
-import java.util.Enumeration;
-import java.util.NoSuchElementException;
-import com.sun.tools.hat.internal.model.JavaHeapObject;
-
-public class CompositeEnumeration implements Enumeration<JavaHeapObject> {
-    Enumeration<JavaHeapObject> e1;
-    Enumeration<JavaHeapObject> e2;
-
-    public CompositeEnumeration(Enumeration<JavaHeapObject> e1, Enumeration<JavaHeapObject> e2) {
-        this.e1 = e1;
-        this.e2 = e2;
-    }
-
-    public boolean hasMoreElements() {
-        return e1.hasMoreElements() || e2.hasMoreElements();
-    }
-
-    public JavaHeapObject nextElement() {
-        if (e1.hasMoreElements()) {
-            return e1.nextElement();
-        }
-
-        if (e2.hasMoreElements()) {
-            return e2.nextElement();
-        }
-
-        throw new NoSuchElementException();
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/util/Misc.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,112 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.util;
-import java.util.*;
-
-/**
- * Miscellaneous functions I couldn't think of a good place to put.
- *
- * @author      Bill Foote
- */
-
-
-public class Misc {
-
-    private static char[] digits = { '0', '1', '2', '3', '4', '5', '6', '7',
-                                     '8', '9', 'a', 'b', 'c', 'd', 'e', 'f' };
-
-    public final static String toHex(int addr) {
-        char[] buf = new char[8];
-        int i = 0;
-        for (int s = 28; s >= 0; s -= 4) {
-            buf[i++] = digits[(addr >> s) & 0xf];
-        }
-        return "0x" + new String(buf);
-    }
-
-    public final static String toHex(long addr) {
-        return "0x" + Long.toHexString(addr);
-    }
-
-    public final static long parseHex(String value) {
-        long result = 0;
-        if (value.length() < 2 || value.charAt(0) != '0' ||
-            value.charAt(1) != 'x') {
-            return -1L;
-        }
-        for(int i = 2; i < value.length(); i++) {
-            result *= 16;
-            char ch = value.charAt(i);
-            if (ch >= '0' && ch <= '9') {
-                result += (ch - '0');
-            } else if (ch >= 'a' && ch <= 'f') {
-                result += (ch - 'a') + 10;
-            } else if (ch >= 'A' && ch <= 'F') {
-                result += (ch - 'A') + 10;
-            } else {
-                throw new NumberFormatException("" + ch
-                                        + " is not a valid hex digit");
-            }
-        }
-        return result;
-    }
-
-    public static String encodeHtml(String str) {
-        final int len = str.length();
-        StringBuilder sb = new StringBuilder();
-        for (int i = 0; i < len; i++) {
-            char ch = str.charAt(i);
-            if (ch == '<') {
-                sb.append("&lt;");
-            } else if (ch == '>') {
-                sb.append("&gt;");
-            } else if (ch == '"') {
-                sb.append("&quot;");
-            } else if (ch == '\'') {
-                sb.append("&#039;");
-            } else if (ch == '&') {
-                sb.append("&amp;");
-            } else if (ch < ' ') {
-                sb.append("&#").append((int)ch).append(';');
-            } else {
-                int c = (ch & 0xFFFF);
-                if (c > 127) {
-                    sb.append("&#").append(c).append(';');
-                } else {
-                    sb.append(ch);
-                }
-            }
-        }
-        return sb.toString();
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/internal/util/VectorSorter.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,148 +0,0 @@
-/*
- * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-package com.sun.tools.hat.internal.util;
-import java.util.*;
-
-/**
- * A singleton utility class that sorts a vector.
- * <p>
- * Use:
- * <pre>
- *
- *  Vector v =   <a vector of, say, String objects>;
- *  VectorSorter.sort(v, new Comparer() {
- *      public int compare(Object lhs, Object rhs) {
- *          return ((String) lhs).compareTo((String) rhs);
- *      }
- *  });
- * </pre>
- *
- * @author      Bill Foote
- */
-
-
-public class VectorSorter {
-
-    /**
-     * Sort the given vector, using c for comparison
-    **/
-    static public void sort(Vector<Object> v, Comparer c)  {
-        quickSort(v, c, 0, v.size()-1);
-    }
-
-
-    /**
-     * Sort a vector of strings, using String.compareTo()
-    **/
-    static public void sortVectorOfStrings(Vector<Object> v) {
-        sort(v, new Comparer() {
-            public int compare(Object lhs, Object rhs) {
-                return ((String) lhs).compareTo((String) rhs);
-            }
-        });
-    }
-
-
-    static private void swap(Vector<Object> v, int a, int b) {
-        Object tmp = v.elementAt(a);
-        v.setElementAt(v.elementAt(b), a);
-        v.setElementAt(tmp, b);
-    }
-
-    //
-    // Sorts v between from and to, inclusive.  This is a quick, off-the-top-
-    // of-my-head quicksort:  I haven't put any thought into optimizing it.
-    // I _did_ put thought into making sure it's safe (it will always
-    // terminate).  Worst-case it's O(n^2), but it will usually run in
-    // in O(n log n).  It's well-behaved if the list is already sorted,
-    // or nearly so.
-    //
-    static private void quickSort(Vector<Object> v, Comparer c, int from, int to) {
-        if (to <= from)
-            return;
-        int mid = (from + to) / 2;
-        if (mid != from)
-            swap(v, mid, from);
-        Object pivot = v.elementAt(from);
-                        // Simple-minded, but reasonable
-        int highestBelowPivot = from - 1;
-        int low = from+1;
-        int high = to;
-            // We now move low and high toward eachother, maintaining the
-            // invariants:
-            //      v[i] <= pivot    for all i < low
-            //      v[i] > pivot     for all i > high
-            // As long as these invariants hold, and every iteration makes
-            // progress, we are safe.
-        while (low <= high) {
-            int cmp = c.compare(v.elementAt(low), pivot);
-            if (cmp <= 0) {    // v[low] <= pivot
-                if (cmp < 0) {
-                    highestBelowPivot = low;
-                }
-                low++;
-            } else {
-                int c2;
-                for (;;) {
-                    c2 = c.compare(v.elementAt(high), pivot);
-                        // v[high] > pivot:
-                    if (c2 > 0) {
-                        high--;
-                        if (low > high) {
-                            break;
-                        }
-                    } else {
-                        break;
-                    }
-                }
-                // At this point, low is never == high
-                if (low <= high) {
-                    swap(v, low, high);
-                    if (c2 < 0) {
-                        highestBelowPivot = low;
-                    }
-                    low++;
-                    high--;
-                }
-            }
-        }
-        // Now we just need to sort from from..highestBelowPivot
-        // and from high+1..to
-        if (highestBelowPivot > from) {
-            // pivot == pivot, so ensure algorithm terminates
-            swap(v, from, highestBelowPivot);
-            quickSort(v, c, from, highestBelowPivot-1);
-        }
-        quickSort(v, c, high+1, to);
-    }
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/resources/hat.js	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,1473 +0,0 @@
-/*
- * Copyright (c) 2005, 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.
- */
-
-/*
- * The Original Code is HAT. The Initial Developer of the
- * Original Code is Bill Foote, with contributions from others
- * at JavaSoft/Sun.
- */
-
-var hatPkg = Packages.com.sun.tools.hat.internal;
-
-/**
- * This is JavaScript interface for heap analysis using HAT
- * (Heap Analysis Tool). HAT classes are referred from
- * this file. In particular, refer to classes in hat.model 
- * package.
- * 
- * HAT model objects are wrapped as convenient script objects so that
- * fields may be accessed in natural syntax. For eg. Java fields can be
- * accessed with obj.field_name syntax and array elements can be accessed
- * with array[index] syntax. 
- */
-
-// returns an enumeration that wraps elements of
-// the input enumeration elements.
-function wrapperEnumeration(e) {
-    return new java.util.Enumeration() {
-        hasMoreElements: function() {
-            return e.hasMoreElements();
-        },
-        nextElement: function() {
-            return wrapJavaValue(e.nextElement());
-        }
-    };
-}
-
-// returns an enumeration that filters out elements
-// of input enumeration using the filter function.
-function filterEnumeration(e, func, wrap) {
-    var next = undefined;
-    var index = 0;
-
-    function findNext() {
-        var tmp;
-        while (e.hasMoreElements()) {
-            tmp = e.nextElement();
-            index++;
-            if (wrap) {
-                tmp = wrapJavaValue(tmp);
-            }
-            if (func(tmp, index, e)) {
-                next = tmp;
-                return;
-            }
-        }
-    }
-
-    return new java.util.Enumeration() {
-        hasMoreElements: function() {
-            findNext();
-            return next != undefined;
-        },
-
-        nextElement: function() {
-            if (next == undefined) {
-                // user may not have called hasMoreElements?
-                findNext();
-            }
-            if (next == undefined) {
-                throw "NoSuchElementException";
-            }
-            var res = next;
-            next = undefined;
-            return res;
-        }
-    };
-}
-
-// enumeration that has no elements ..
-var emptyEnumeration = new java.util.Enumeration() {
-        hasMoreElements: function() { 
-            return false;
-        },
-        nextElement: function() {
-            throw "NoSuchElementException";
-        }
-    };
-
-function wrapRoot(root) {
-    if (root) {
-        return {
-            id: root.idString,
-            description: root.description,
-            referrer: wrapJavaValue(root.referer),
-            type: root.typeName
-        };
-    } else {
-        return null;
-    }
-}
-
-function JavaClassProto() {    
-    function jclass(obj) {
-        return obj['wrapped-object'];
-    }
-
-    // return whether given class is subclass of this class or not
-    this.isSubclassOf = function(other) {
-        var tmp = jclass(this);
-        var otherid = objectid(other);
-        while (tmp != null) {
-            if (otherid.equals(tmp.idString)) {
-                return true;
-            }
-            tmp = tmp.superclass;
-        }
-        return false;
-    }
-
-    // return whether given class is superclass of this class or not
-    this.isSuperclassOf = function(other) {
-        return other.isSubclassOf(this); 
-    }
-
-    // includes direct and indirect superclasses
-    this.superclasses = function() {
-        var res = new Array();
-        var tmp = this.superclass;
-        while (tmp != null) {
-            res[res.length] = tmp;
-            tmp = tmp.superclass;
-        }
-        return res;
-    }
-
-    /**
-     * Returns an array containing subclasses of this class.
-     *
-     * @param indirect should include indirect subclasses or not.
-     *                 default is true.
-     */
-    this.subclasses = function(indirect) {
-        if (indirect == undefined) indirect = true;
-        var classes = jclass(this).subclasses;
-        var res = new Array();
-        for (var i in classes) {
-            var subclass = wrapJavaValue(classes[i]);
-            res[res.length] = subclass;
-            if (indirect) {
-                res = res.concat(subclass.subclasses());
-            }
-        }
-        return res;
-    }
-    this.toString = function() { return jclass(this).toString(); }
-}
-
-var theJavaClassProto = new JavaClassProto();
-
-// Script wrapper for HAT model objects, values.
-// wraps a Java value as appropriate for script object
-function wrapJavaValue(thing) {
-    if (thing == null || thing == undefined ||
-        thing instanceof hatPkg.model.HackJavaValue) {
-	return null;
-    } 
-    
-    if (thing instanceof hatPkg.model.JavaValue) {
-        // map primitive values to closest JavaScript primitives
-        if (thing instanceof hatPkg.model.JavaBoolean) {
-            return thing.toString() == "true";
-        } else if (thing instanceof hatPkg.model.JavaChar) {
-            return thing.toString() + '';
-        } else {
-            return java.lang.Double.parseDouble(thing.toString());
-        }			
-    } else {
-        // wrap Java object as script object
-        return wrapJavaObject(thing);		
-    }
-}
-
-// wrap Java object with appropriate script object
-function wrapJavaObject(thing) {
-
-    // HAT Java model object wrapper. Handles all cases 
-    // (instance, object/primitive array and Class objects)	
-    function javaObject(jobject) {		
-        // FIXME: Do I need this? or can I assume that these would
-        // have been resolved already?
-        if (jobject instanceof hatPkg.model.JavaObjectRef) {
-            jobject = jobject.dereference();
-            if (jobject instanceof hatPkg.model.HackJavaValue) {
-                print(jobject);
-                return null;
-            }
-        }
-
-        if (jobject instanceof hatPkg.model.JavaObject) {
-            return new JavaObjectWrapper(jobject);
-        } else if (jobject instanceof hatPkg.model.JavaClass) {
-            return new JavaClassWrapper(jobject);
-        } else if (jobject instanceof hatPkg.model.JavaObjectArray) {
-            return new JavaObjectArrayWrapper(jobject);
-        } else if (jobject instanceof hatPkg.model.JavaValueArray) {
-            return new JavaValueArrayWrapper(jobject);
-        } else {
-            print("unknown heap object type: " + jobject.getClass());
-            return jobject;
-        }
-    }
-    
-    // returns wrapper for Java instances
-    function JavaObjectWrapper(instance) {
-        var things = instance.fields;
-        var fields = instance.clazz.fieldsForInstance;
-    		
-        // instance fields can be accessed in natural syntax
-        return new JSAdapter() {
-            __getIds__ : function() {
-                    var res = new Array(fields.length);
-                    for (var i in fields) {
-                        res[i] = fields[i].name;
-                    }
-                    return res;
-            },
-            __has__ : function(name) {
-                    for (var i in fields) {
-                        if (name == fields[i].name) return true;
-                    }
-                    return name == 'class' || name == 'toString' ||
-                           name == 'wrapped-object';
-            },
-            __get__ : function(name) {
-    
-                    for (var i in fields) {
-                        if(fields[i].name == name) {
-                            return wrapJavaValue(things[i]);
-                        }
-                    }
-    
-                    if (name == 'class') {
-                        return wrapJavaValue(instance.clazz);
-                    } else if (name == 'wrapped-object') {
-                        return instance;
-                    } 
-    
-                    return undefined;
-            },
-            __call__: function(name) {
-                if (name == 'toString') {
-                    return instance.toString();
-                } else {
-                    return undefined;
-                }
-            } 
-        }				
-    }
-
-
-    // return wrapper for Java Class objects
-    function JavaClassWrapper(jclass) {	
-        var fields = jclass.statics;
-    
-        // to access static fields of given Class cl, use 
-        // cl.statics.<static-field-name> syntax
-        this.statics = new JSAdapter() {
-            __getIds__ : function() {
-                var res = new Array(fields.length);
-                for (var i in fields) {
-                    res[i] = fields[i].field.name;
-                }
-                return res;
-            },
-            __has__ : function(name) {
-                for (var i in fields) {
-                    if (name == fields[i].field.name) {
-                        return true;
-                    }					
-                }
-                return false;
-            },
-            __get__ : function(name) {
-                for (var i in fields) {
-                    if (name == fields[i].field.name) {
-                        return wrapJavaValue(fields[i].value);	
-                    }					
-                }
-                return undefined;
-            }
-        }
-    		
-        if (jclass.superclass != null) {
-            this.superclass = wrapJavaValue(jclass.superclass);
-        } else {
-            this.superclass = null;
-        }
-
-        this.loader = wrapJavaValue(jclass.getLoader());
-        this.signers = wrapJavaValue(jclass.getSigners());
-        this.protectionDomain = wrapJavaValue(jclass.getProtectionDomain());
-        this.instanceSize = jclass.instanceSize;
-        this.name = jclass.name; 
-        this.fields = jclass.fields;
-        this['wrapped-object'] = jclass;
-    }
-
-    for (var i in theJavaClassProto) {
-        if (typeof theJavaClassProto[i] == 'function') {
-           JavaClassWrapper.prototype[i] = theJavaClassProto[i];
-        }
-    }
-    
-    // returns wrapper for Java object arrays
-    function JavaObjectArrayWrapper(array) {
-        var elements = array.elements;
-        // array elements can be accessed in natural syntax
-        // also, 'length' property is supported.
-        return new JSAdapter() {
-            __getIds__ : function() {
-                var res = new Array(elements.length);
-                for (var i = 0; i < elements.length; i++) {
-                    res[i] = String(i);
-                }
-                return res;
-            },
-            __has__: function(name) {
-                return (name >= 0 && name < elements.length)  ||
-                        name == 'length' || name == 'class' ||
-                        name == 'toString' || name == 'wrapped-object';
-            },
-            __get__ : function(name) {
-                if (name >= 0 && name < elements.length) {
-                    return wrapJavaValue(elements[name]);
-                } else if (name == 'length') {
-                    return elements.length;
-                } else if (name == 'class') {
-                    return wrapJavaValue(array.clazz);
-                } else if (name == 'wrapped-object') {
-                    return array;
-                } else {
-                    return undefined;
-                }				
-            },
-            __call__: function(name) {
-                if (name == 'toString') {
-                    return array.toString();
-                } else {
-                    return undefined;
-                }
-            } 
-        }			
-    }
-    
-    // returns wrapper for Java primitive arrays
-    function JavaValueArrayWrapper(array) {
-        var type = String(java.lang.Character.toString(array.elementType));
-        var elements = array.elements;
-        // array elements can be accessed in natural syntax
-        // also, 'length' property is supported.
-        return new JSAdapter() {
-            __getIds__ : function() {
-                var r = new Array(array.length);
-                for (var i = 0; i < array.length; i++) {
-                    r[i] = String(i);
-                }
-                return r;
-            },
-            __has__: function(name) {
-                return (name >= 0 && name < array.length) ||
-                        name == 'length' || name == 'class' ||
-                        name == 'toString' || name == 'wrapped-object';
-            },
-            __get__: function(name) {
-                if (name >= 0 && name < array.length) {
-                    return elements[name];
-                }
-    
-                if (name == 'length') {
-                    return array.length;
-                } else if (name == 'wrapped-object') {
-                    return array;
-                } else if (name == 'class') {
-                    return wrapJavaValue(array.clazz);
-                } else {
-                    return undefined;
-                }
-            },
-            __call__: function(name) {
-                if (name == 'toString') {
-                    return array.valueString(true);
-                } else {
-                    return undefined;
-                }
-            } 
-        }
-    }
-    return javaObject(thing);
-}
-
-// unwrap a script object to corresponding HAT object
-function unwrapJavaObject(jobject) {
-    if (!(jobject instanceof hatPkg.model.JavaHeapObject)) {
-        try {
-            jobject = jobject["wrapped-object"];
-        } catch (e) {
-            print("unwrapJavaObject: " + jobject + ", " + e);
-            jobject = undefined;
-        }
-    }
-    return jobject;
-}
-
-/**
- * readHeapDump parses a heap dump file and returns script wrapper object.
- *
- * @param file  Heap dump file name
- * @param stack flag to tell if allocation site traces are available
- * @param refs  flag to tell if backward references are needed or not
- * @param debug debug level for HAT
- * @return heap as a JavaScript object
- */
-function readHeapDump(file, stack, refs, debug) {
-
-    // default value of debug is 0
-    if (!debug) debug = 0;
-
-    // by default, we assume no stack traces
-    if (!stack) stack = false;
-
-    // by default, backward references are resolved
-    if (!refs) refs = true;
-
-    // read the heap dump 
-    var heap = hatPkg.parser.HprofReader.readFile(file, stack, debug);
-
-    // resolve it
-    heap.resolve(refs);
-
-    // wrap Snapshot as convenient script object
-    return wrapHeapSnapshot(heap);
-}
-
-/**
- * The result object supports the following methods:
- * 
- *  forEachClass  -- calls a callback for each Java Class
- *  forEachObject -- calls a callback for each Java object
- *  findClass -- finds Java Class of given name
- *  findObject -- finds object from given object id
- *  objects -- returns all objects of given class as an enumeration
- *  classes -- returns all classes in the heap as an enumeration
- *  reachables -- returns all objects reachable from a given object
- *  livepaths -- returns an array of live paths because of which an
- *               object alive.
- *  describeRef -- returns description for a reference from a 'from' 
- *              object to a 'to' object.
- */
-function wrapHeapSnapshot(heap) {
-    function getClazz(clazz) {
-        if (clazz == undefined) clazz = "java.lang.Object";
-        var type = typeof(clazz);
-        if (type == "string") {
-            clazz = heap.findClass(clazz);		
-        } else if (type == "object") {
-            clazz = unwrapJavaObject(clazz);
-        } else {
-            throw "class expected";;
-        }
-        return clazz;
-    }
-
-    // return heap as a script object with useful methods.
-    return {
-        snapshot: heap,
-
-        /**
-         * Class iteration: Calls callback function for each
-         * Java Class in the heap. Default callback function 
-         * is 'print'. If callback returns true, the iteration 
-         * is stopped.
-         *
-         * @param callback function to be called.
-         */
-        forEachClass: function(callback) {
-            if (callback == undefined) callback = print;
-            var classes = this.snapshot.classes;
-            while (classes.hasMoreElements()) {
-                if (callback(wrapJavaValue(classes.nextElement())))
-                    return;
-            }
-        },
-
-        /**
-         * Returns an Enumeration of all roots.
-         */
-        roots: function() {
-            var e = this.snapshot.roots;
-            return new java.util.Enumeration() {
-                hasMoreElements: function() {
-                    return e.hasMoreElements();
-                },
-                nextElement: function() {
-                    return wrapRoot(e.nextElement());
-                }
-            };
-        },
-
-        /**
-         * Returns an Enumeration for all Java classes.
-         */
-        classes: function() {
-            return wrapIterator(this.snapshot.classes, true);
-        },
-
-        /**
-         * Object iteration: Calls callback function for each
-         * Java Object in the heap. Default callback function 
-         * is 'print'.If callback returns true, the iteration 
-         * is stopped.
-         *
-         * @param callback function to be called. 
-         * @param clazz Class whose objects are retrieved.
-         *        Optional, default is 'java.lang.Object'
-         * @param includeSubtypes flag to tell if objects of subtypes
-         *        are included or not. optional, default is true.
-         */
-        forEachObject: function(callback, clazz, includeSubtypes) {
-            if (includeSubtypes == undefined) includeSubtypes = true;
-            if (callback == undefined) callback = print;
-            clazz = getClazz(clazz);
-
-            if (clazz) {
-                var instances = clazz.getInstances(includeSubtypes);
-                while (instances.hasNextElements()) {
-                    if (callback(wrapJavaValue(instances.nextElement())))
-                        return;
-                }
-            }
-        },
-
-        /** 
-         * Returns an enumeration of Java objects in the heap.
-         * 
-         * @param clazz Class whose objects are retrieved.
-         *        Optional, default is 'java.lang.Object'
-         * @param includeSubtypes flag to tell if objects of subtypes
-         *        are included or not. optional, default is true.
-         * @param where (optional) filter expression or function to
-         *        filter the objects. The expression has to return true
-         *        to include object passed to it in the result array. 
-         *        Built-in variable 'it' refers to the current object in 
-         *        filter expression.
-         */
-        objects: function(clazz, includeSubtypes, where) {
-            if (includeSubtypes == undefined) includeSubtypes = true;
-            if (where) {
-                if (typeof(where) == 'string') {
-                    where = new Function("it", "return " + where);
-                }
-            }
-            clazz = getClazz(clazz);
-            if (clazz) {
-                var instances = clazz.getInstances(includeSubtypes);
-                if (where) {
-                    return filterEnumeration(instances, where, true);
-                } else {
-                    return wrapperEnumeration(instances);
-                }
-            } else {
-                return emptyEnumeration;
-            }
-        },
-
-        /**
-         * Find Java Class of given name.
-         * 
-         * @param name class name
-         */
-        findClass: function(name) {
-            var clazz = this.snapshot.findClass(name + '');
-            return wrapJavaValue(clazz);
-        },
-
-        /**
-         * Find Java Object from given object id
-         *
-         * @param id object id as string
-         */
-        findObject: function(id) {
-            return wrapJavaValue(this.snapshot.findThing(id));
-        },
-
-        /**
-         * Returns an enumeration of objects in the finalizer
-         * queue waiting to be finalized.
-         */
-        finalizables: function() {
-            var tmp = this.snapshot.getFinalizerObjects();
-            return wrapperEnumeration(tmp);
-        },
- 
-        /**
-         * Returns an array that contains objects referred from the
-         * given Java object directly or indirectly (i.e., all 
-         * transitively referred objects are returned).
-         *
-         * @param jobject Java object whose reachables are returned.
-         */
-        reachables: function (jobject) {
-            return reachables(jobject, this.snapshot.reachableExcludes);
-        },
-
-        /**
-         * Returns array of paths of references by which the given 
-         * Java object is live. Each path itself is an array of
-         * objects in the chain of references. Each path supports
-         * toHtml method that returns html description of the path.
-         *
-         * @param jobject Java object whose live paths are returned
-         * @param weak flag to indicate whether to include paths with
-         *             weak references or not. default is false.
-         */
-        livepaths: function (jobject, weak) {
-            if (weak == undefined) {
-                weak = false;
-            }
-
-            function wrapRefChain(refChain) {
-                var path = new Array();
-
-                // compute path array from refChain
-                var tmp = refChain;
-                while (tmp != null) {
-                    var obj = tmp.obj;
-                    path[path.length] = wrapJavaValue(obj);
-                    tmp = tmp.next;
-                }
-
-                function computeDescription(html) {
-                    var root = refChain.obj.root;
-                    var desc = root.description;
-                    if (root.referer) {
-                        var ref = root.referer;
-                        desc += " (from " + 
-                            (html? toHtml(ref) : ref.toString()) + ')';
-                    }
-                    desc += '->';
-                    var tmp = refChain;
-                    while (tmp != null) {
-                        var next = tmp.next;
-                        var obj = tmp.obj;
-                        desc += html? toHtml(obj) : obj.toString();
-                        if (next != null) {
-                            desc += " (" + 
-                                    obj.describeReferenceTo(next.obj, heap)  + 
-                                    ") ->";
-                        }
-                        tmp = next;
-                    }
-                    return desc;
-                }
-
-                return new JSAdapter() {
-                    __getIds__ : function() {
-                        var res = new Array(path.length);
-                        for (var i = 0; i < path.length; i++) {
-                            res[i] = String(i);
-                        }
-                        return res;
-                    },
-                    __has__ : function (name) {
-                        return (name >= 0 && name < path.length) ||
-                            name == 'length' || name == 'toHtml' ||
-                            name == 'toString';
-                    },
-                    __get__ : function(name) {
-                        if (name >= 0 && name < path.length) {
-                            return path[name];
-                        } else if (name == 'length') {
-                            return path.length;
-                        } else {
-                            return undefined;
-                        }
-                    },
-                    __call__: function(name) {
-                        if (name == 'toHtml') {
-                            return computeDescription(true);
-                        } else if (name == 'toString') {
-                            return computeDescription(false);
-                        } else {
-                            return undefined;
-                        }
-                    }
-                };
-            }
-
-            jobject = unwrapJavaObject(jobject);
-            var refChains = this.snapshot.rootsetReferencesTo(jobject, weak);
-            var paths = new Array(refChains.length);
-            for (var i in refChains) {
-                paths[i] = wrapRefChain(refChains[i]);
-            }
-            return paths;
-        },
-
-        /**
-         * Return description string for reference from 'from' object
-         * to 'to' Java object.
-         *
-         * @param from source Java object
-         * @param to destination Java object
-         */
-        describeRef: function (from, to) {
-            from = unwrapJavaObject(from);
-            to = unwrapJavaObject(to);
-            return from.describeReferenceTo(to, this.snapshot);
-        },
-    };
-}
-
-// per-object functions
-
-/**
- * Returns allocation site trace (if available) of a Java object
- *
- * @param jobject object whose allocation site trace is returned
- */
-function allocTrace(jobject) {
-    try {
-        jobject = unwrapJavaObject(jobject);			
-        var trace = jobject.allocatedFrom;
-        return (trace != null) ? trace.frames : null;
-    } catch (e) {
-        print("allocTrace: " + jobject + ", " + e);
-        return null;
-    }
-}
-
-/**
- * Returns Class object for given Java object
- *
- * @param jobject object whose Class object is returned
- */
-function classof(jobject) {
-    jobject = unwrapJavaObject(jobject);
-    return wrapJavaValue(jobject.clazz);
-}
-
-/**
- * Find referers (a.k.a in-coming references). Calls callback
- * for each referrer of the given Java object. If the callback 
- * returns true, the iteration is stopped.
- *
- * @param callback function to call for each referer
- * @param jobject object whose referers are retrieved
- */
-function forEachReferrer(callback, jobject) {
-    jobject = unwrapJavaObject(jobject);
-    var refs = jobject.referers;
-    while (refs.hasMoreElements()) {
-        if (callback(wrapJavaValue(refs.nextElement()))) {
-            return;
-        }
-    }
-}
-
-/**
- * Compares two Java objects for object identity.
- *
- * @param o1, o2 objects to compare for identity
- */
-function identical(o1, o2) {
-    return objectid(o1) == objectid(o2);
-}
-
-/**
- * Returns Java object id as string
- *
- * @param jobject object whose id is returned
- */
-function objectid(jobject) {
-    try {
-        jobject = unwrapJavaObject(jobject);
-        return String(jobject.idString);
-    } catch (e) {
-        print("objectid: " + jobject + ", " + e);
-        return null;
-    }
-}
-
-/**
- * Prints allocation site trace of given object
- *
- * @param jobject object whose allocation site trace is returned
- */
-function printAllocTrace(jobject) {
-    var frames = this.allocTrace(jobject);
-    if (frames == null || frames.length == 0) {
-        print("allocation site trace unavailable for " + 
-              objectid(jobject));
-        return;
-    }    
-    print(objectid(jobject) + " was allocated at ..");
-    for (var i in frames) {
-        var frame = frames[i];
-        var src = frame.sourceFileName;
-        if (src == null) src = '<unknown source>';
-        print('\t' + frame.className + "." +
-             frame.methodName + '(' + frame.methodSignature + ') [' +
-             src + ':' + frame.lineNumber + ']');
-    }
-}
-
-/**
- * Returns an enumeration of referrers of the given Java object.
- *
- * @param jobject Java object whose referrers are returned.
- */
-function referrers(jobject) {
-    try {
-        jobject = unwrapJavaObject(jobject);
-        return wrapperEnumeration(jobject.referers);
-    } catch (e) {
-        print("referrers: " + jobject + ", " + e);
-        return emptyEnumeration;
-    }
-}
-
-/**
- * Returns an array that contains objects referred from the
- * given Java object.
- *
- * @param jobject Java object whose referees are returned.
- */
-function referees(jobject) {
-    var res = new Array();
-    jobject = unwrapJavaObject(jobject);
-    if (jobject != undefined) {
-        try {
-            jobject.visitReferencedObjects(
-                new hatPkg.model.JavaHeapObjectVisitor() {
-                    visit: function(other) { 
-                        res[res.length] = wrapJavaValue(other);
-                    },
-                    exclude: function(clazz, field) { 
-                        return false; 
-                    },
-                    mightExclude: function() { 
-                        return false; 
-                    }
-                });
-        } catch (e) {
-            print("referees: " + jobject + ", " + e);
-        }
-    }
-    return res;
-}
-
-/**
- * Returns an array that contains objects referred from the
- * given Java object directly or indirectly (i.e., all 
- * transitively referred objects are returned).
- *
- * @param jobject Java object whose reachables are returned.
- * @param excludes optional comma separated list of fields to be 
- *                 removed in reachables computation. Fields are
- *                 written as class_name.field_name form.
- */
-function reachables(jobject, excludes) {
-    if (excludes == undefined) {
-        excludes = null;
-    } else if (typeof(excludes) == 'string') {
-        var st = new java.util.StringTokenizer(excludes, ",");
-        var excludedFields = new Array();
-        while (st.hasMoreTokens()) {
-            excludedFields[excludedFields.length] = st.nextToken().trim();
-        }
-        if (excludedFields.length > 0) { 
-            excludes = new hatPkg.model.ReachableExcludes() {
-                        isExcluded: function (field) {
-                            for (var index in excludedFields) {
-                                if (field.equals(excludedFields[index])) {
-                                    return true;
-                                }
-                            }
-                            return false;
-                        }
-                    };
-        } else {
-            // nothing to filter...
-            excludes = null;
-        }
-    } else if (! (excludes instanceof hatPkg.model.ReachableExcludes)) {
-        excludes = null;
-    }
-
-    jobject = unwrapJavaObject(jobject);
-    var ro = new hatPkg.model.ReachableObjects(jobject, excludes);  
-    var tmp = ro.reachables;
-    var res = new Array(tmp.length);
-    for (var i in tmp) {
-        res[i] = wrapJavaValue(tmp[i]);
-    }
-    return res;
-}
-
-
-/**
- * Returns whether 'from' object refers to 'to' object or not.
- *
- * @param from Java object that is source of the reference.
- * @param to Java object that is destination of the reference.
- */
-function refers(from, to) {
-    try {
-        var tmp = unwrapJavaObject(from);
-        if (tmp instanceof hatPkg.model.JavaClass) {
-            from = from.statics;
-        } else if (tmp instanceof hatPkg.model.JavaValueArray) {
-            return false;
-        }
-        for (var i in from) {
-            if (identical(from[i], to)) {
-                return true;
-            }
-        }
-    } catch (e) {
-        print("refers: " + from + ", " + e);
-    }
-    return false;
-}
-
-/**
- * If rootset includes given jobject, return Root
- * object explanining the reason why it is a root.
- *
- * @param jobject object whose Root is returned
- */
-function root(jobject) {
-    try {
-        jobject = unwrapJavaObject(jobject);
-        return wrapRoot(jobject.root);
-    } catch (e) {
-        return null;
-    }
-}
-
-/**
- * Returns size of the given Java object
- *
- * @param jobject object whose size is returned
- */
-function sizeof(jobject) {
-    try {
-        jobject = unwrapJavaObject(jobject);
-        return jobject.size;
-    } catch (e) {
-        print("sizeof: " + jobject + ", " + e);
-        return null;
-    }
-}
-
-/**
- * Returns String by replacing Unicode chars and
- * HTML special chars (such as '<') with entities.
- *
- * @param str string to be encoded
- */
-function encodeHtml(str) {
-    return hatPkg.util.Misc.encodeHtml(str);
-}
-
-/**
- * Returns HTML string for the given object.
- *
- * @param obj object for which HTML string is returned.
- */
-function toHtml(obj) {
-    if (obj == null) {
-        return "null";
-    } 
-
-    if (obj == undefined) {
-        return "undefined";
-    } 
-
-    var tmp = unwrapJavaObject(obj);
-    if (tmp != undefined) {
-        var id = tmp.idString;
-        if (tmp instanceof Packages.com.sun.tools.hat.internal.model.JavaClass) {
-            var name = tmp.name;
-            return "<a href='/class/" + id + "'>class " + name + "</a>";
-        } else {
-            var name = tmp.clazz.name;
-            return "<a href='/object/" + id + "'>" +
-                   name + "@" + id + "</a>";
-        }
-    } else if (obj instanceof Object) {
-        if (Array.isArray(obj)) {
-            // script array
-            var res = "[ ";
-            for (var i in obj) {
-                res += toHtml(obj[i]);
-                if (i != obj.length - 1) {
-                    res += ", ";
-                }
-            } 
-            res += " ]";
-            return res;
-        } else {
-            // if the object has a toHtml function property
-            // just use that...
-            if (typeof(obj.toHtml) == 'function') {
-                return obj.toHtml();
-            } else {
-                // script object
-                var res = "{ ";
-                for (var i in obj) {
-                    res +=  i + ":" + toHtml(obj[i]) + ", ";
-                }
-                res += "}";
-                return res;
-            }
-        }
-    } else {
-        // a Java object
-        obj = wrapIterator(obj);
-        // special case for enumeration
-        if (obj instanceof java.util.Enumeration) {
-            var res = "[ ";
-            while (obj.hasMoreElements()) {
-                res += toHtml(obj.nextElement()) + ", ";
-            }
-            res += "]";
-            return res; 
-        } else {
-            return obj;
-        }
-    }
-}
-
-/*
- * Generic array/iterator/enumeration [or even object!] manipulation 
- * functions. These functions accept an array/iteration/enumeration
- * and expression String or function. These functions iterate each 
- * element of array and apply the expression/function on each element.
- */
-
-// private function to wrap an Iterator as an Enumeration
-function wrapIterator(itr, wrap) {
-    if (itr instanceof java.util.Iterator) {
-        return new java.util.Enumeration() {
-                   hasMoreElements: function() {
-                       return itr.hasNext();
-                   },
-                   nextElement: function() {
-                       return wrap? wrapJavaValue(itr.next()) : itr.next();
-                   }
-               };
-    } else {
-        return itr;
-    }
-}
-
-/**
- * Converts an enumeration/iterator/object into an array
- *
- * @param obj enumeration/iterator/object
- * @return array that contains values of enumeration/iterator/object
- */
-function toArray(obj) {	
-    obj = wrapIterator(obj);
-    if (obj instanceof java.util.Enumeration) {
-        var res = new Array();
-        while (obj.hasMoreElements()) {
-            res[res.length] = obj.nextElement();
-        }
-        return res;
-    } else if (obj instanceof Array) {
-        return obj;
-    } else {
-        var res = new Array();
-        for (var index in obj) {
-            res[res.length] = obj[index];
-        }
-        return res;
-    }
-}
-
-/**
- * Returns whether the given array/iterator/enumeration contains 
- * an element that satisfies the given boolean expression specified 
- * in code. 
- *
- * @param array input array/iterator/enumeration that is iterated
- * @param code  expression string or function 
- * @return boolean result
- *
- * The code evaluated can refer to the following built-in variables. 
- *
- * 'it' -> currently visited element
- * 'index' -> index of the current element
- * 'array' -> array that is being iterated
- */
-function contains(array, code) {
-    array = wrapIterator(array);
-    var func = code;
-    if (typeof(func) != 'function') {
-        func = new Function("it", "index", "array",  "return " + code);
-    }
-
-    if (array instanceof java.util.Enumeration) {
-        var index = 0;
-        while (array.hasMoreElements()) {
-            var it = array.nextElement();
-            if (func(it, index, array)) {
-                return true;
-            }
-            index++;
-        }
-    } else {
-        for (var index in array) {
-            var it = array[index];
-            if (func(it, String(index), array)) {
-                return true;
-            }
-        }
-    }
-    return false;
-}
-
-/**
- * concatenates two arrays/iterators/enumerators.
- *
- * @param array1 array/iterator/enumeration
- * @param array2 array/iterator/enumeration
- *
- * @return concatenated array or composite enumeration
- */
-function concat(array1, array2) {
-    array1 = wrapIterator(array1);
-    array2 = wrapIterator(array2);
-    if (array1 instanceof Array && array2 instanceof Array) {
-        return array1.concat(array2);
-    } else if (array1 instanceof java.util.Enumeration &&
-               array2 instanceof java.util.Enumeration) {
-        return new Packages.com.sun.tools.hat.internal.util.CompositeEnumeration(array1, array2);
-    } else {
-        return undefined;
-    }
-}
-
-/**
- * Returns the number of array/iterator/enumeration elements 
- * that satisfy the given boolean expression specified in code. 
- * The code evaluated can refer to the following built-in variables. 
- *
- * @param array input array/iterator/enumeration that is iterated
- * @param code  expression string or function 
- * @return number of elements
- *
- * 'it' -> currently visited element
- * 'index' -> index of the current element
- * 'array' -> array that is being iterated
- */
-function count(array, code) {
-    if (code == undefined) {
-        return length(array);
-    }
-    array = wrapIterator(array);
-    var func = code;
-    if (typeof(func) != 'function') {
-        func = new Function("it", "index", "array",  "return " + code);
-    }
-
-    var result = 0;
-    if (array instanceof java.util.Enumeration) {
-        var index = 0;
-        while (array.hasMoreElements()) {
-            var it = array.nextElement();
-            if (func(it, index, array)) {
-                result++;
-            }
-            index++;
-        }
-    } else {
-        for (var index in array) {
-            var it = array[index];
-            if (func(it, index, array)) {
-                result++;
-            }
-        }
-    }
-    return result;
-}
-
-/**
- * filter function returns an array/enumeration that contains 
- * elements of the input array/iterator/enumeration that satisfy 
- * the given boolean expression. The boolean expression code can 
- * refer to the following built-in variables. 
- *
- * @param array input array/iterator/enumeration that is iterated
- * @param code  expression string or function 
- * @return array/enumeration that contains the filtered elements
- *
- * 'it' -> currently visited element
- * 'index' -> index of the current element
- * 'array' -> array that is being iterated
- * 'result' -> result array
- */
-function filter(array, code) {
-    array = wrapIterator(array);
-    var func = code;
-    if (typeof(code) != 'function') {
-        func = new Function("it", "index", "array", "result", "return " + code);
-    }
-    if (array instanceof java.util.Enumeration) {
-        return filterEnumeration(array, func, false);
-    } else {
-        var result = new Array();
-        for (var index in array) {
-            var it = array[index];
-            if (func(it, String(index), array, result)) {
-                result[result.length] = it;
-            }
-        }
-        return result;
-    }
-}
-
-/**
- * Returns the number of elements of array/iterator/enumeration.
- *
- * @param array input array/iterator/enumeration that is iterated
- */
-function length(array) {
-    array = wrapIterator(array);
-    if (array instanceof Array) {
-        return array.length;
-    } else if (array instanceof java.util.Enumeration) {
-        var cnt = 0;
-        while (array.hasMoreElements()) {
-            array.nextElement(); 
-            cnt++;
-        }
-        return cnt;
-    } else {
-        var cnt = 0;
-        for (var index in array) {
-            cnt++;
-        }
-        return cnt;
-    }
-}
-
-/**
- * Transforms the given object or array by evaluating given code
- * on each element of the object or array. The code evaluated
- * can refer to the following built-in variables. 
- *
- * @param array input array/iterator/enumeration that is iterated
- * @param code  expression string or function 
- * @return array/enumeration that contains mapped values
- *
- * 'it' -> currently visited element
- * 'index' -> index of the current element
- * 'array' -> array that is being iterated
- * 'result' -> result array
- *
- * map function returns an array/enumeration of values created 
- * by repeatedly calling code on each element of the input
- * array/iterator/enumeration.
- */
-function map(array, code) {
-    array = wrapIterator(array);
-    var func = code;
-    if(typeof(code) != 'function') {
-        func = new Function("it", "index", "array", "result", "return " + code);
-    }
-
-    if (array instanceof java.util.Enumeration) {
-        var index = 0;
-        var result = new java.util.Enumeration() {
-            hasMoreElements: function() {
-                return array.hasMoreElements();
-            },
-            nextElement: function() {
-                return func(array.nextElement(), index++, array, result);
-            }
-        };
-        return result;
-    } else {
-        var result = new Array();
-        for (var index in array) {
-            var it = array[index];
-            result[result.length] = func(it, String(index), array, result);
-        }
-        return result;
-    }
-}
-
-// private function used by min, max functions
-function minmax(array, code) {
-    if (typeof(code) == 'string') {
-        code = new Function("lhs", "rhs", "return " + code);
-    }
-    array = wrapIterator(array);
-    if (array instanceof java.util.Enumeration) {
-        if (! array.hasMoreElements()) {
-            return undefined;
-        }
-        var res = array.nextElement();
-        while (array.hasMoreElements()) {
-            var next = array.nextElement();
-            if (code(next, res)) {
-                res = next;
-            }
-        }
-        return res;
-    } else {
-        if (array.length == 0) {
-            return undefined;
-        }
-        var res = array[0];
-        for (var index = 1; index < array.length; index++) {
-            if (code(array[index], res)) {
-                res = array[index];
-            }
-        } 
-        return res;
-    }
-}
-
-/**
- * Returns the maximum element of the array/iterator/enumeration
- *
- * @param array input array/iterator/enumeration that is iterated
- * @param code (optional) comparision expression or function
- *        by default numerical maximum is computed.
- */
-function max(array, code) {
-    if (code == undefined) {
-        code = function (lhs, rhs) { return lhs > rhs; }
-    }
-    return minmax(array, code);
-}
-
-/**
- * Returns the minimum element of the array/iterator/enumeration
- *
- * @param array input array/iterator/enumeration that is iterated
- * @param code (optional) comparision expression or function
- *        by default numerical minimum is computed.
- */
-function min(array, code) {
-    if (code == undefined) {
-        code = function (lhs, rhs) { return lhs < rhs; }
-    } 
-    return minmax(array, code);
-}
-
-/**
- * sort function sorts the input array. optionally accepts
- * code to compare the elements. If code is not supplied,
- * numerical sort is done.
- *
- * @param array input array/iterator/enumeration that is sorted
- * @param code  expression string or function 
- * @return sorted array 
- *
- * The comparison expression can refer to the following
- * built-in variables:
- *
- * 'lhs' -> 'left side' element
- * 'rhs' -> 'right side' element
- */
-function sort(array, code) {
-    // we need an array to sort, so convert non-arrays
-    array = toArray(array);
-
-    // by default use numerical comparison
-    var func = code;
-    if (code == undefined) {
-        func = function(lhs, rhs) { return lhs - rhs; };
-    } else if (typeof(code) == 'string') {
-        func = new Function("lhs", "rhs", "return " + code);
-    }
-    return array.sort(func);
-}
-
-/**
- * Returns the sum of the elements of the array
- *
- * @param array input array that is summed.
- * @param code optional expression used to map
- *        input elements before sum.
- */
-function sum(array, code) {
-    array = wrapIterator(array);
-    if (code != undefined) {
-        array = map(array, code);
-    }
-    var result = 0;
-    if (array instanceof java.util.Enumeration) {
-        while (array.hasMoreElements()) {
-            result += Number(array.nextElement());
-        }
-    } else {
-        for (var index in array) {
-            result += Number(array[index]);
-        }
-    }
-    return result;
-}
-
-/**
- * Returns array of unique elements from the given input 
- * array/iterator/enumeration.
- *
- * @param array from which unique elements are returned.
- * @param code optional expression (or function) giving unique
- *             attribute/property for each element.
- *             by default, objectid is used for uniqueness.
- */
-function unique(array, code) {
-    array = wrapIterator(array);
-    if (code == undefined) {
-        code = new Function("it", "return objectid(it);");
-    } else if (typeof(code) == 'string') {
-        code = new Function("it", "return " + code);
-    }
-    var tmp = new Object();
-    if (array instanceof java.util.Enumeration) {
-        while (array.hasMoreElements()) {
-            var it = array.nextElement();
-            tmp[code(it)] = it;
-        }
-    } else {
-        for (var index in array) {
-            var it = array[index];
-            tmp[code(it)] = it;
-        }
-    }
-    var res = new Array();
-    for (var index in tmp) {
-        res[res.length] = tmp[index];
-    }
-    return res;
-}
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/resources/oqlhelp.html	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,808 +0,0 @@
-<!--
-Copyright (c) 2005, 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.
--->
-
-<html>
-<head>
-<style>
-.key  { color: red; font-weight: bold }
-</style>
-<title>
-Object Query Language (OQL)
-</title>
-</head>
-<body>
-<h1>Object Query Language (OQL)</h1>
-
-<p>
-OQL is SQL-like query language to query Java heap. OQL allows to filter/select information
-wanted from Java heap. While pre-defined queries such as "show all instances of class X"
-are already supported by HAT, OQL adds more flexibility. OQL is based on JavaScript expression
-language.
-</p>
-
-<p>
-OQL query is of the form
-
-<pre>
-<code>
-         <span class="key">select</span> &lt;JavaScript expression to select&gt;
-         [ <span class="key">from</span> [<span class="key">instanceof</span>] &lt;class name&gt; &lt;identifier&gt;
-         [ <span class="key">where</span> &lt;JavaScript boolean expression to filter&gt; ] ]
-</code>
-</pre>
-where class name is fully qualified Java class name (example: java.net.URL) or array class name.
-[C is char array name, [Ljava.io.File; is name of java.io.File[] and so on. 
-Note that fully qualified class name does not always uniquely identify a 
-Java class at runtime. There may be more than one Java class with the same 
-name but loaded by different loaders. So, class name is permitted to be
-id string of the class object.
-
-If <span class="key">instanceof</span> keyword is used, subtype objects are selected. If this 
-keyword is not specified, only the instances of exact class specified are selected. Both
-<span class="key">from</span> and <span class="key">where</span> clauses are optional.
-</p>
-
-
-<p>
-In <span class="key">select</span> and (optional) <span class="key">where</span> clauses, the expression 
-used in JavaScript expression. Java heap objects are wrapped as convenient script objects so that 
-fields may be accessed in natural syntax. For example, Java fields can be accessed with obj.field_name 
-syntax and array elements can be accessed with array[index] syntax. Each Java object selected is 
-bound to a JavaScript variable of the identifier name specified in <span class="key">from</span> clause.
-</p>
-
-<h2>OQL Examples</h2>
-
-<ul>
-<li>select all Strings of length 100 or more
-<pre>
-<code>
-    select s from java.lang.String s where s.value.length >= 100
-</code>
-</pre>
-<li>select all int arrays of length 256 or more
-<pre>
-<code>
-    select a from [I a where a.length >= 256
-</code>
-</pre>
-<li>show content of Strings that match a regular expression
-<pre>
-<code>
-    select s.value.toString() from java.lang.String s 
-    where /java/.test(s.value.toString())
-</code>
-</pre>
-<li>show path value of all File objects
-<pre>
-<code</b>
-    select file.path.value.toString() from java.io.File file
-</code>
-</pre>
-<li>show names of all ClassLoader classes
-<pre>
-<code>
-    select <a href="#classof">classof</a>(cl).name 
-    from instanceof java.lang.ClassLoader cl
-</code>
-</pre>
-<li>show instances of the Class identified by given id string
-<pre>
-<code>
-    select o from instanceof 0xd404b198 o
-</code>
-</pre>
-Note that 0xd404b198 is id of a Class (in a session). This is found by
-looking at the id shown in that class's page.
-</ul>
-
-<h2>OQL built-in objects, functions</h2>
-
-<h3>heap object</h3>
-
-The <b>heap</b> built-in object supports the following methods:
-
-<ul> 
-<li><b>heap.forEachClass</b> -- calls a callback function for each Java Class
-<pre>
-<code>
-    heap.forEachClass(callback);
-</code>
-</pre>
-<li><b>heap.forEachObject</b> -- calls a callback function for each Java object
-<pre>
-<code>
-    heap.forEachObject(callback, clazz, includeSubtypes);
-</code>
-</pre>
-<code>clazz</code> is the class whose instances are selected. If not specified, defaults to java.lang.Object. <code>includeSubtypes</code> is a boolean flag 
-that specifies whether to include subtype instances or not. Default value of 
-this flag is true.
-<a name="findClass"></a>
-<li><b>heap.findClass</b> -- finds Java Class of given name
-<pre>
-<code>
-    heap.findClass(className);
-</code>
-</pre>
-where <code>className</code> is name of the class to find. The resulting Class 
-object has following properties:
-<ul>
-<li>name - name of the class.
-<li>superclass - Class object for super class (or null if java.lang.Object).
-<li>statics - name, value pairs for static fields of the Class.
-<li>fields - array of field objects. field object has name, signature
-properties.
-<li>loader - ClassLoader object that loaded this class.
-<li>signers - signers that signed this class.
-<li>protectionDomain - protection domain to which this class belongs.
-</ul>
-Class objects have the following methods:
-<ul>
-<li>isSubclassOf - tests whether given class is direct or indirect 
-subclass of this class or not.
-<li>isSuperclassOf - tests whether given Class is direct or indirect
-superclass of this class or not.
-<li>subclasses - returns array of direct and indirect subclasses.
-<li>superclasses - returns array of direct and indirect superclasses.
-</ul>
-<a name="findObject"></a>
-<li><b>heap.findObject</b> -- finds object from given object id
-<pre>
-<code>
-    heap.findObject(stringIdOfObject);
-</code>
-</pre>
-<a name="classes"></a>
-<li><b>heap.classes</b> -- returns an enumeration of all Java classes
-<a name="objects"></a>
-<li><b>heap.objects</b> -- returns an enumeration of Java objects 
-<pre>
-<code>
-    heap.objects(clazz, [includeSubtypes], [filter])
-</code>
-</pre>
-<code>clazz</code> is the class whose instances are selected. If not specified, defaults to java.lang.Object. <code>includeSubtypes</code> is a boolean flag 
-that specifies whether to include subtype instances or not. Default value of 
-this flag is true. This method accepts an optional filter expression to filter
-the result set of objects.
-<a name="finalizables"></a>
-<li><b>heap.finalizables</b> -- returns an enumeration of Java objects that are
-pending to be finalized.
-<li><b>heap.livepaths</b> -- return an array of paths by which a given object 
-is alive. This method accepts optional second parameter that is a boolean
-flag. This flag tells whether to include paths with weak reference(s) or not.
-By default, paths with weak reference(s) are not included.
-<pre>
-<code>
-    select heap.livepaths(s) from java.lang.String s
-</code>
-</pre>
-Each element of this array itself is another array. The later array is 
-contains an objects that are in the 'reference chain' of the path.
-<li><b>heap.roots</b> -- returns an Enumeration of Roots of the heap. 
-<a name="rootobj"></a>
-Each Root object has the following properties:
-<ul>
-<li>id - String id of the object that is referred by this root
-<li>type - descriptive type of Root (JNI Global, JNI Local, Java Static etc)
-<li>description - String description of the Root
-<li>referrer - Thread Object or Class object that is responsible for this root or null
-</ul>
-</ul>
-
-Examples:
-<ul>
-<li>access static field 'props' of class java.lang.System
-<pre>
-<code>
-    select heap.findClass("java.lang.System").statics.props
-</code>
-</pre>
-<li>get number of fields of java.lang.String class 
-<pre>
-<code>
-    select heap.findClass("java.lang.String").fields.length
-</code>
-</pre>
-<li> find the object whose object id is given
-<pre>
-<code>
-    select heap.findObject("0xf3800b58")
-</code>
-</pre>
-<li>select all classes that have name pattern java.net.*
-<pre>
-<code>
-    select <a href="#filter">filter</a>(heap.classes(), "/java.net./.test(it.name)")
-</code>
-</pre>
-</ul>
-
-<h3>functions on individual objects</h3>
-
-<ul>
-<li><a href="#allocTrace">allocTrace(jobject)</a>
-<li><a href="#classof">classof(jobject)</a>
-<li><a href="#forEachReferrer">forEachReferrer(callback, jobject)</a>
-<li><a href="#identical">identical(o1, o2)</a>
-<li><a href="#objectid">objectid(jobject)</a>
-<li><a href="#reachables">reachables(jobject, excludedFields)</a>
-<li><a href="#referrers">referrers(jobject)</a>
-<li><a href="#referees">referees(jobject)</a>
-<li><a href="#refers">refers(jobject)</a>
-<li><a href="#root">root(jobject)</a>
-<li><a href="#sizeof">sizeof(jobject)</a>
-<li><a href="#toHtml">toHtml(obj)</a>
-</ul>
-
-<a name="allocTrace"></a>
-<h4>allocTrace function</h4>
-
-This returns allocation site trace of a given Java object if available.
-allocTrace returns array of frame objects. Each frame object has the following
-properties:
-<ul>
-<li>className - name of the Java class whose method is running in the frame.
-<li>methodName - name of the Java method running in the frame.
-<li>methodSignature - signature of the Java method running in the frame.
-<li>sourceFileName - name of source file of the Java class running in the frame.
-<li>lineNumber - source line number within the method.
-</ul>
-
-<a name="classof"></a>
-<h4>classof function</h4>
-
-Returns Class object of a given Java Object. The result object supports the
-following properties:
-<ul>
-<li>name - name of the class.
-<li>superclass - Class object for super class (or null if java.lang.Object).
-<li>statics - name, value pairs for static fields of the Class.
-<li>fields - array of field objects. Field objects have name, signature
-properties.
-<li>loader - ClassLoader object that loaded this class.
-<li>signers - signers that signed this class.
-<li>protectionDomain - protection domain to which this class belongs.
-</ul>
-Class objects have the following methods:
-<ul>
-<li>isSubclassOf - tests whether given class is direct or indirect 
-subclass of this class or not.
-<li>isSuperclassOf - tests whether given Class is direct or indirect
-superclass of this class or not.
-<li>subclasses - returns array of direct and indirect subclasses.
-<li>superclasses - returns array of direct and indirect superclasses.
-</ul>
-
-Examples:
-<ul>
-<li>show class name of each Reference type object
-<pre>
-<code>
-    select classof(o).name from instanceof java.lang.ref.Reference o
-</code>
-<li>show all subclasses of java.io.InputStream
-<pre>
-<code>
-    select heap.findClass("java.io.InputStream").subclasses()
-</code>
-<li>show all superclasses of java.io.BufferedInputStream
-<pre>
-<code>
-    select heap.findClass("java.io.BufferedInputStream").superclasses()
-</code>
-</pre>
-</ul>
-
-<a name="forEachReferrer"></a>
-<h4>forEachReferrer function</h4>
-
-calls a callback function for each referrer of a given Java object.
-
-<a name="identical"></a>
-<h4>identical function</h4>
-<p>
-Returns whether two given Java objects are identical or not.
-</p>
-Example:
-<pre>
-<code>
-    select identical(heap.findClass("Foo").statics.bar, heap.findClass("AnotherClass").statics.bar)
-</code>
-</pre>
-
-<a name="objectid"></a>
-<h4>objectid function</h4>
-
-<p>
-Returns String id of a given Java object. This id can be passed to
-<a href="#findObject">heap.findObject</a> and may also be used to compare
-objects for identity.
-</p>
-Example:
-<pre>
-<code>
-    select objectid(o) from java.lang.Object o
-</code>
-</pre>
-
-<a name="reachables"></a>
-<h4>reachables function</h4>
-<p>
-Returns an array of Java objects that are transitively referred from the
-given Java object. Optionally accepts a second parameter that is comma
-separated field names to be excluded from reachability computation.
-Fields are written in class_name.field_name pattern.
-</p>
-Examples: 
-<ul>
-<li>print all reachable objects from each Properties instance.
-<pre>
-<code>
-    select reachables(p) from java.util.Properties p
-</code>
-</pre>
-<li>print all reachables from each java.net.URL but omit the objects reachable
-via the fields specified.
-<pre>
-<code>
-    select reachables(u, 'java.net.URL.handler') from java.net.URL u
-</code>
-</pre>
-</ul>
-
-<a name="referrers"></a>
-<h4>referrers function</h4>
-<p>
-Returns an enumeration of Java objects that hold reference to a given Java
-object.
-</p>
-Examples:
-<ul>
-<li> print number of referrers for each java.lang.Object instance
-<pre>
-<code>
-    select count(referrers(o)) from java.lang.Object o
-</code>
-</pre>
-<li>print referrers for each java.io.File object
-<pre>
-<code>
-    select referrers(f) from java.io.File f
-</code>
-</pre>
-<li>print URL objects only if referred by 2 or more 
-<pre>
-<code>
-    select u from java.net.URL u where count(referrers(u)) > 2
-</code>
-</pre>
-</ul>
-
-<a name="referees"></a>
-<h4>referees function</h4>
-<p>
-Returns an array of Java objects to which the given Java
-object directly refers to.
-</p>
-Example: to print all static reference fields of java.io.File class
-<pre>
-<code>
-    select referees(<a href="#findClass">heap.findClass</a>("java.io.File"))
-</code>
-</pre>
-
-<a name="refers"></a>
-<h4>refers function</h4>
-<p>
-Returns whether first Java object refers to second Java object or not.
-</p>
-
-<a name="root"></a>
-<h4>root function</h4>
-<p>
-If given object is a member of root set of objects, this function returns
-a descriptive <a href="#rootobj">Root object</a> describing why it is so.
-If given object is not a root, then this function returns null.
-</p>
-
-<a name="sizeof"></a>
-<h4>sizeof function</h4>
-
-Returns size of the given Java object in bytes
-Example: 
-<pre>
-<code>
-    select sizeof(o) from [I o
-</code>
-</pre>
-
-<a name="toHtml"></a>
-<h4>toHtml function</h4>
-
-Returns HTML string for the given Java object. Note that this is called
-automatically for objects selected by select expression. But, it may be useful
-to print more complex output.
-
-Example: print hyperlink in bold font weight
-<pre>
-<code>
-    select "&lt;b&gt;" + toHtml(o) + "&lt;/b&gt;" from java.lang.Object o
-</code>
-</pre>
-
-<h3>Selecting multiple values</h3>
-<p>
-Multiple values can be selected using JavaScript object literals or arrays.
-</p>
-
-Example: show name and thread for each thread object
-<pre>
-<code>
-    select { name: t.name? t.name.toString() : "null", thread: t } 
-    from instanceof java.lang.Thread t
-</code>
-</pre>
-
-<h3>array/iterator/enumeration manipulation functions</h3>
-
-<p>
-These functions accept an array/iterator/enumeration and an 
-expression string [or a callback function] as input. These functions iterate 
-the array/iterator/enumeration and apply the expression (or function) on 
-each element. Note that JavaScript objects are associative arrays. So, 
-these functions may also be used with arbitrary JavaScript objects.
-</p>
-
-<ul>
-<li><a href="#concat">concat(array1/enumeration1, array2/enumeration2)</a>
-<li><a href="#contains">contains(array/enumeration, expression)</a>
-<li><a href="#count">count(array/enumeration, expression)</a>
-<li><a href="#filter">filter(array/enumeration, expression)</a>
-<li><a href="#length">length(array/enumeration)</a>
-<li><a href="#map">map(array/enumeration, expression)</a>
-<li><a href="#max">max(array/enumeration, [expression])</a>
-<li><a href="#min">min(array/enumeration, [expression])</a>
-<li><a href="#sort">sort(array/enumeration, [expression])</a>
-<li><a href="#sum">sum(array/enumeration, [expression])</a>
-<li><a href="#toArray">toArray(array/enumeration)</a>
-<li><a href="#unique">unique(array/enumeration, [expression])</a>
-</ul>
-
-<a name="concat"></a>
-<h4>concat function</h4>
-<p>
-Concatenates two arrays or enumerations (i.e., returns composite
-enumeration).
-</p>
-
-<a name="contains"></a>
-<h4>contains function</h4>
-<p>
-Returns whether the given array/enumeration contains an element
-the given boolean expression specified in code. The code evaluated
-can refer to the following built-in variables.
-</p>
-<ul>
-<li>it -> currently visited element
-<li>index -> index of the current element
-<li>array -> array/enumeration that is being iterated
-</ul>
-Example: select all Properties objects that are referred by 
-some static field some class.
-<pre>
-<code>
-    select p from java.util.Properties p
-    where contains(<a href="#referrers">referrers</a>(p), "<a href="#classof">classof</a>(it).name == 'java.lang.Class'")
-</code>
-</pre>
-
-<a name="count"></a>
-<h4>count function</h4>
-<p>
-count function returns the count of elements of the input array/enumeration 
-that satisfy the given boolean expression. The boolean expression code can 
-refer to the following built-in variables.
-</p>
-<ul>
-<li>it -> currently visited element
-<li>index -> index of the current element
-<li>array -> array/enumeration that is being iterated
-</ul>
-Example: print number of classes that have specific name pattern
-<pre>
-<code>
-    select count(<a href="#classes">heap.classes()</a>, "/java.io./.test(it.name)")
-</code>
-</pre>
-
-<a name="filter"></a>
-<h4>filter function</h4>
-<p>
-filter function returns an array/enumeration that contains elements 
-of the input array/enumeration that satisfy the given boolean 
-expression. The boolean expression code can refer to the following built-in
-variables.
-</p>
-<ul>
-<li>it -> currently visited element
-<li>index -> index of the current element
-<li>array -> array/enumeration that is being iterated
-<li>result -> result array/enumeration
-</ul>
-Examples:
-<ul>
-<li>show all classes that have java.io.* name pattern
-<pre>
-<code>
-    select filter(<a href="#classes">heap.classes</a>(), "/java.io./.test(it.name)")
-</code>
-</pre>
-<li> show all referrers of URL object where the referrer is not from
-java.net package
-<pre>
-<code>
-    select filter(<a href="#referrers">referrers</a>(u), "! /java.net./.test(<a href="#classof">classof</a>(it).name)")
-    from java.net.URL u
-</code>
-</pre>
-</ul>
-
-<a name="length"></a>
-<h4>length function</h4>
-<p>
-length function returns number of elements of an array/enumeration.
-</p>
-
-<a name="map"></a>
-<h4>map function</h4>
-<p>
-Transforms the given array/enumeration by evaluating given code
-on each element. The code evaluated can refer to the following built-in 
-variables.
-</p>
-<ul>
-<li>it -> currently visited element
-<li>index -> index of the current element
-<li>array -> array/enumeration that is being iterated
-<li>result -> result array/enumeration
-</ul>
-<p>
-map function returns an array/enumeration of values created by repeatedly
-calling code on each element of input array/enumeration.
-</p>
-Example: show all static fields of java.io.File with name and value
-<pre>
-<code>
-    select map(<a href="#findClass">heap.findClass</a>("java.io.File").statics, "index + '=' + <a href="#toHtml">toHtml</a>(it)")
-</code>
-</pre>
-
-<a name="max"></a>
-<h4>max function</h4>
-<p>
-returns the maximum element of the  given array/enumeration. 
-Optionally accepts code expression to compare elements of the array. 
-By default numerical comparison is used. The comparison expression can 
-use the following built-in variables:
-</p>
-<ul>
-<li>lhs -> left side element for comparison
-<li>rhs -> right side element for comparison
-</ul>
-Examples:
-<ul>
-<li>find the maximum length of any String instance
-<pre>
-<code>
-    select max(map(heap.objects('java.lang.String', false), 'it.value.length'))
-</code>
-</pre>
-<li>find string instance that has the maximum length
-<pre>
-<code>
-    select max(heap.objects('java.lang.String'), 'lhs.value.length > rhs.value.length')
-</code>
-</pre>
-</ul>
-
-<a name="min"></a>
-<h4>min function</h4>
-<p>
-returns the minimum element of the  given array/enumeration. Optionally 
-accepts code expression to compare elements of the array. By default numerical
-comparison is used. The comparison expression can use the following built-in 
-variables:
-</p>
-<ul>
-<li>lhs -> left side element for comparison
-<li>rhs -> right side element for comparison
-</ul>
-Examples:
-<ul>
-<li>find the minimum size of any Vector instance
-<pre>
-<code>
-    select min(map(heap.objects('java.util.Vector', false), 'it.elementData.length'))
-</code>
-</pre>
-<li>find Vector instance that has the maximum length
-<pre>
-<code>
-    select min(heap.objects('java.util.Vector'), 'lhs.elementData.length < rhs.elementData.length')
-</code>
-</ul>
-
-<a name="sort"></a>
-<h4>sort function</h4>
-<p>
-sorts given array/enumeration. Optionally accepts code expression to
-compare elements of the array. By default numerical comparison is used.
-The comparison expression can use the following built-in variables:
-</p>
-<ul>
-<li>lhs -> left side element for comparison
-<li>rhs -> right side element for comparison
-</ul>
-Examples:
-<ul>
-<li> print all char[] objects in the order of size.
-<pre>
-<code>
-    select sort(<a href="#objects">heap.objects</a>('[C'), '<a href="#sizeof">sizeof</a>(lhs) - sizeof(rhs)')
-</code>
-</pre>
-<li> print all char[] objects in the order of size but print
-size as well.
-<pre>
-<code>
-    select <a href="#map">map</a>(sort(<a href="#objects">heap.objects</a>('[C'), '<a href="#sizeof">sizeof</a>(lhs) - sizeof(rhs)'), '{ size: sizeof(it), obj: it }')
-</code>
-</pre>
-</ul>
-
-<a name="sum"></a>
-<h4>sum function</h4>
-<p>
-This function returns the sum of all the elements of the given input array or
-enumeration. Optionally, accepts an expression as second param. This is used
-to map the input elements before summing those.
-</p>
-Example: return sum of sizes of the reachable objects from each Properties object
-<pre>
-<code>
-    select sum(<a href="#map">map</a>(<a href="#reachables">reachables</a>(p), '<a href="#sizeof">sizeof</a>(it)')) 
-    from java.util.Properties p
-
-    // or omit the map as in ...
-    select sum(<a href="#reachables">reachables</a>(p), '<a href="#sizeof">sizeof</a>(it)') 
-    from java.util.Properties p
-</code>
-</code>
-</pre>
-
-<a name="toArray"></a>
-<h4>toArray function</h4>
-<p>
-This function returns an array that contains elements of the input
-array/enumeration.
-</p>
-
-<a name="unique"></a>
-<h4>unique function</h4>
-<p>
-This function returns an array/enumeration containing unique elements of the 
-given input array/enumeration
-</p>
-Example: select unique char[] instances referenced from Strings. Note that
-more than one String instance can share the same char[] for the content.
-<pre>
-<code>
-   // number of unique char[] instances referenced from any String
-   select count(unique(map(heap.objects('java.lang.String'), 'it.value')))
-
-   // total number of Strings
-   select count(heap.objects('java.lang.String'))
-</code>
-</pre>
-    
-<h3>More complex examples</h3>
-
-<h4>Print histogram of each class loader and number of classes loaded by it</h4>
-
-<pre>
-<code>
-   select <a href="#map">map</a>(<a href="#sort">sort</a>(map(heap.objects('java.lang.ClassLoader'), 
-   '{ loader: it, count: it.classes.elementCount }'), 'lhs.count < rhs.count'),
-   'toHtml(it) + "&lt;br&gt;"')
-</code>
-</pre>
-<p>
-The above query uses the fact that, <b>java.lang.ClassLoader</b> has a private 
-field called <b>classes</b> of type <b>java.util.Vector</b> and Vector has a 
-private field named <b>elementCount</b> that is number of elements in the 
-vector. We select multiple values (loader, count) using JavaScript object 
-literal and map function. We sort the result by count (i.e., number of classes 
-loaded) using sort function with comparison expression.
-</p>
-
-<h4>Show parent-child chain for each class loader instance</h4>
-
-<pre>
-<code>
-   select <a href="#map">map</a>(heap.objects('java.lang.ClassLoader'),
-      function (it) {
-         var res = '';
-         while (it != null) {
-            res += toHtml(it) + "-&gt;";
-            it = it.parent;
-         }
-         res += "null";
-         return res + "&lt;br&gt;";
-      })
-</code>
-</pre>
-<p>
-Note that we use <b>parent</b> field of <b>java.lang.ClassLoader</b> class
-and walk until parent is null using the callback function to map call.
-</p>
-
-<h4>Printing value of all System properties</h4>
-
-<pre>
-<code>
-   select <a href="#map">map</a>(<a href="#filter">filter(<a href="#findClass">heap.findClass</a>('java.lang.System').statics.props.table, 'it != null'), 
-            function (it) {
-                var res = "";
-                while (it != null) {
-                    res += it.key.value.toString() + '=' +
-                           it.value.value.toString() + '&lt;br&gt;';
-                    it = it.next;
-                }
-                return res;
-            });
-</code>
-</pre>
-<p>
-The above query uses the following facts:
-<ul>
-<li>java.lang.System has static field by name 'props' of type java.util.Properties.
-<li>java.util.Properties has field by 'table' of type java.util.Hashtable$Entry
-(this field is inherited from java.util.Hashtable). This is the hashtable
-buckets array.
-<li>java.util.Hashtable$Entry has 'key', 'value' and 'next' fields. Each
-entry points the next entry (or null) in the same hashtable bucket.
-<li>java.lang.String class has 'value' field of type char[].
-</ul>
-<p>
-<b>Note that this query (and many other queries) may not be stable - because
-private fields of Java platform classes may be modified/removed without any
-notification! (implementation detail)</b>. But, using such queries on user 
-classes may be safe - given that user has the control over the classes.
-</p>
-
-</body>
-</html>
--- a/jdk/src/jdk.dev/share/classes/com/sun/tools/hat/resources/platform_names.txt	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,29 +0,0 @@
-boolean[
-char[
-float[
-double[
-byte[
-short[
-int[
-long[
-sun.
-java.
-javax.accessibility
-javax.crypto.
-javax.imageio.
-javax.naming.
-javax.net.
-javax.print.
-javax.rmi.
-javax.security.
-javax.sound.
-javax.sql.
-javax.swing.
-javax.transaction.
-javax.xml.parsers.
-javax.xml.transform.
-org.ietf.jgss.
-org.omg.
-org.w3c.dom.
-org.xml.sax.
-
--- a/jdk/src/jdk.hprof.agent/unix/native/libhprof/hprof_md.c	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/jdk.hprof.agent/unix/native/libhprof/hprof_md.c	Wed Jul 05 20:35:10 2017 +0200
@@ -290,19 +290,7 @@
     Dl_info dlinfo;
 
     libdir[0] = 0;
-#if defined(LINUX) || defined(_ALLBSD_SOURCE) || defined(AIX)
-    addr = (void*)&Agent_OnLoad;
-#else
-    /* Just using &Agent_OnLoad will get the first external symbol with
-     *   this name in the first .so, which may not be libhprof.so.
-     *   On Solaris we can actually ask for the address of our Agent_OnLoad.
-     */
-    addr = dlsym(RTLD_SELF, "Agent_OnLoad");
-    /* Just in case the above didn't work (missing linker patch?). */
-    if ( addr == NULL ) {
-        addr = (void*)&Agent_OnLoad;
-    }
-#endif
+    addr = (void*)&md_get_prelude_path;
 
     /* Use dladdr() to get the full path to libhprof.so, which we use to find
      *  the prelude file.
--- a/jdk/src/jdk.jdi/share/classes/com/sun/jdi/Accessible.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/jdk.jdi/share/classes/com/sun/jdi/Accessible.java	Wed Jul 05 20:35:10 2017 +0200
@@ -40,8 +40,8 @@
 public interface Accessible {
 
     /**
-     * Returns the Java<sup><font size=-2>TM</font></sup>
-     * programming language modifiers, encoded in an integer.
+     * Returns the Java&trade; programming language modifiers, encoded
+     * in an integer.
      * <p>
      * The modifier encodings are defined in
      * <cite>The Java&trade; Virtual Machine Specification</cite>
--- a/jdk/src/jdk.jdi/share/classes/com/sun/jdi/ClassNotLoadedException.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/jdk.jdi/share/classes/com/sun/jdi/ClassNotLoadedException.java	Wed Jul 05 20:35:10 2017 +0200
@@ -45,7 +45,7 @@
  * <li>There can be no guarantee that running the appropriate class
  * loader won't cause a deadlock in loading the
  * class. Class loaders can consist of arbitrary
- * Java<sup><font size=-2>TM</font></sup> programming language code and the
+ * Java&trade; programming language code and the
  * class loading methods are usually synchronized. Most of the work
  * done by a debugger happens when threads are suspended. If another
  * application thread is suspended within the same class loader,
--- a/jdk/src/jdk.jdi/share/classes/com/sun/jdi/Locatable.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/jdk.jdi/share/classes/com/sun/jdi/Locatable.java	Wed Jul 05 20:35:10 2017 +0200
@@ -36,10 +36,10 @@
 @jdk.Exported
 public interface Locatable {
     /**
-     * Returns the {@link Location} of this mirror, if there
-     * is executable code associated with it. Note that both
-     * Java<SUP><FONT SIZE="-2">TM</FONT></SUP> programming
-     * language methods and native methods have executable code.
+     * Returns the {@link Location} of this mirror, if there is
+     * executable code associated with it. Note that both Java&trade;
+     * programming language methods and native methods have executable
+     * code.
      * Returns null for abstract methods, since abstract methods
      * have no executable code.
      *
--- a/jdk/src/jdk.jdi/share/classes/com/sun/jdi/request/AccessWatchpointRequest.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/jdk.jdi/share/classes/com/sun/jdi/request/AccessWatchpointRequest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -31,8 +31,7 @@
  * Request for notification when the contents of a field are accessed
  * in the target VM.
  * This event will be triggered when the specified field is accessed
- * by Java<SUP><FONT SIZE="-2">TM</FONT></SUP> programming
- * language code or by a
+ * by Java&trade; programming language code or by a
  * Java Native Interface (JNI) get function (<code>Get&lt;Type&gt;Field,
  * GetStatic&lt;Type&gt;Field</code>).
  * Access by JDI does not trigger this event.
--- a/jdk/src/jdk.jdi/share/classes/com/sun/jdi/request/ModificationWatchpointRequest.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/jdk.jdi/share/classes/com/sun/jdi/request/ModificationWatchpointRequest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -30,7 +30,7 @@
 /**
  * Request for notification when a field is set.
  * This event will be triggered when a value is assigned to the specified
- * field with a Java<SUP><FONT SIZE="-2">TM</FONT></SUP> programming
+ * field with a Java&trade; programming
  * language statement (assignment, increment, etc) or by a
  * Java Native Interface (JNI) set function (<code>Set&lt;Type&gt;Field,
  * SetStatic&lt;Type&gt;Field</code>).
--- a/jdk/src/jdk.jdi/share/classes/jdi-overview.html	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/jdk.jdi/share/classes/jdi-overview.html	Wed Jul 05 20:35:10 2017 +0200
@@ -1,11 +1,10 @@
 <!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML//EN">
 <html>
   <head>
-    <title>Java(tm) Debug Interface</title>
+    <title>Java&trade; Debug Interface</title>
   </head>
   <body>
-	The Java<sup><font size="-2">TM</font></sup>
- Debug Interface (JDI) is a high level Java
+	The Java&trade; Debug Interface (JDI) is a high level Java
 API providing information useful for debuggers and similar
 systems needing access to the running state of a (usually remote)
 virtual machine.
--- a/jdk/src/jdk.rmic/share/classes/sun/rmi/rmic/RMIGenerator.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/jdk.rmic/share/classes/sun/rmi/rmic/RMIGenerator.java	Wed Jul 05 20:35:10 2017 +0200
@@ -79,7 +79,7 @@
      * Examine and consume command line arguments.
      * @param argv The command line arguments. Ignore null
      * and unknown arguments. Set each consumed argument to null.
-     * @param error Report any errors using the main.error() methods.
+     * @param main Report any errors using the main.error() methods.
      * @return true if no errors, false otherwise.
      */
     public boolean parseArgs(String argv[], Main main) {
--- a/jdk/src/jdk.rmic/share/classes/sun/rmi/rmic/RemoteClass.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/jdk.rmic/share/classes/sun/rmi/rmic/RemoteClass.java	Wed Jul 05 20:35:10 2017 +0200
@@ -111,7 +111,7 @@
      * the remote methods implemented by this class, i.e. all of the
      * methods in the class's remote interfaces.
      *
-     * The methods in the array are ordered according to the comparision
+     * The methods in the array are ordered according to the comparison
      * of the strings consisting of their method name followed by their
      * type signature, so each method's index in the array corresponds
      * to its "operation number" in the JDK 1.1 version of the
--- a/jdk/src/sample/share/jmx/jmx-scandir/index.html	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/src/sample/share/jmx/jmx-scandir/index.html	Wed Jul 05 20:35:10 2017 +0200
@@ -33,11 +33,11 @@
  SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 -->
 
-    <title>JMX(TM) "scandir" Example</title>
+    <title>JMX&trade; "scandir" Example</title>
   </head>
   <body>
 
-  <h1><center>Java<font size="-1"><sup>TM</sup></font> Management Extensions (JMX<font size="-1"><sup>TM</sup></font>) <i>scandir</i> Example</center></h1>
+  <h1><center>Java&trade; Management Extensions (JMX&trade;) <i>scandir</i> Example</center></h1>
 
   <h2><a name="h2-Introduction">Introduction</a></h2>
   <ul>
@@ -1197,7 +1197,7 @@
        <p>Another common best practice when you want
           to improve interoperability is to use directly
           the Notification base classes provided in the
-          JMX<sup>TM</sup> API. Do not create your own
+          JMX&trade; API. Do not create your own
           subclasses of these standard classes.
        </p>
        <p>Indeed, if you code your own subclass, a generic
@@ -1974,7 +1974,7 @@
         More information on SSL authentication can be obtained from the <a
         href="http://java.sun.com/javase/6/docs/technotes/guides/security/jsse/JSSERefGuide.html#HowSSLWorks"
         title="How SSL Works"
-        >Java<sup>TM</sup> Secure Socket Extension (JSSE) Reference Guide</a>.
+        >Java&trade; Secure Socket Extension (JSSE) Reference Guide</a>.
     </p>
     <p>To start jconsole with our provided keystore and
     truststore, go to the scandir example root directory and
@@ -2202,13 +2202,13 @@
      <li><a
         href="http://java.sun.com/javase/6/docs/technotes/guides/security/jsse/JSSERefGuide.html#HowSSLWorks"
         title="The JSSE Reference Guide"
-        >Java<sup>TM</sup> Secure Socket Extension (JSSE) Reference Guide</a>:
-        comprehensive documentation about the Java<sup>TM</sup> Secure Socket
+        >Java&trade; Secure Socket Extension (JSSE) Reference Guide</a>:
+        comprehensive documentation about the Java&trade; Secure Socket
         Extension (JSSE)
      </li>
      <li><a href="http://java.sun.com/javase/6/docs/"
          >Java SE 6 Documentation Index</a>: This document covers the
-          Java<sup>TM</sup> Platform, Standard Edition 6 JDK.</li>
+          Java&trade; Platform, Standard Edition 6 JDK.</li>
   </ol>
   <p>
   <hr>
--- a/jdk/test/ProblemList.txt	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/ProblemList.txt	Wed Jul 05 20:35:10 2017 +0200
@@ -379,4 +379,10 @@
 # 8064572 8060736 8062938
 sun/jvmstat/monitor/MonitoredVm/CR6672135.java			generic-all
 
+# 8079273
+demo/jvmti/hprof/CpuOldTest.java            generic-all
+demo/jvmti/hprof/CpuTimesTest.java          generic-all
+demo/jvmti/hprof/OptionsTest.java           generic-all
+demo/jvmti/hprof/StackMapTableTest.java     generic-all
+
 ############################################################################
--- a/jdk/test/TEST.groups	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/TEST.groups	Wed Jul 05 20:35:10 2017 +0200
@@ -534,7 +534,6 @@
   sun/nio/cs/OLD/TestIBMDB.java \
   sun/nio/cs/SJISCanEncode.java \
   sun/nio/cs/Test6254467.java \
-  sun/nio/cs/TestCompoundTest.java \
   sun/nio/cs/TestCp834_SBCS.java \
   sun/nio/cs/TestEUC_TW.java \
   sun/nio/cs/TestISO2022CNDecoder.java \
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/com/sun/crypto/provider/Cipher/KeyWrap/TestCipherKeyWrapperTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,316 @@
+/*
+ * 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 static java.lang.System.out;
+
+import java.lang.Integer;
+import java.lang.String;
+import java.lang.System;
+import java.security.AlgorithmParameters;
+import java.security.InvalidAlgorithmParameterException;
+import java.security.InvalidKeyException;
+import java.security.Key;
+import java.security.KeyPair;
+import java.security.NoSuchAlgorithmException;
+import java.security.KeyPairGenerator;
+import java.security.Provider;
+import java.security.Security;
+import java.security.spec.AlgorithmParameterSpec;
+import java.security.spec.InvalidKeySpecException;
+import java.util.Arrays;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.Random;
+
+import javax.crypto.IllegalBlockSizeException;
+import javax.crypto.NoSuchPaddingException;
+import javax.crypto.SecretKey;
+import javax.crypto.Cipher;
+import javax.crypto.KeyGenerator;
+import javax.crypto.SecretKeyFactory;
+import javax.crypto.spec.PBEKeySpec;
+import javax.crypto.spec.PBEParameterSpec;
+
+/*
+ * @test
+ * @bug 8048599
+ * @summary  Tests for key wrap and unwrap operations
+ */
+
+public class TestCipherKeyWrapperTest {
+    private static final String SUN_JCE = "SunJCE";
+    // Blowfish Variable key length: 32 bits to 448 bits
+    private static final int BLOWFISH_MIN_KEYSIZE = 32;
+    private static final int BLOWFISH_MAX_KEYSIZE = 448;
+    private static final int LINIMITED_KEYSIZE = 128;
+    private static final String NOPADDING = "NoPaDDing";
+    private static final String[] PBE_ALGORITHM_AR = { "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" };
+    private static final String[] MODEL_AR = { "ECb", "pCbC", "cbC", "cFB",
+            "cFB24", "cFB40", "OfB48", "OFB64" };
+    private static final String[] PADDING_AR = { NOPADDING, "PKCS5Padding" };
+
+    private enum AlgorithmWrapper {
+        AESWrap("AES", "AESWrap", -1),
+        AESWrap_128("AES", "AESWrap_128", 128),
+        AESWrap_192("AES", "AESWrap_192", 192),
+        AESWrap_256("AES", "AESWrap_256", 256),
+        DESedeWrap("desede", "DESedeWrap", -1),
+        NegtiveWrap("AES", "DESedeWrap", -1);
+
+        private final String algorithm;
+        private final String wrapper;
+        private final int keySize;
+
+        private AlgorithmWrapper(String algorithm, String wrapper, int kSize) {
+            this.algorithm = algorithm;
+            this.wrapper = wrapper;
+            this.keySize = kSize;
+        }
+
+        public String getAlgorithm() {
+            return algorithm;
+        }
+
+        public String getWrapper() {
+            return wrapper;
+        }
+
+        public int getKeySize() {
+            return keySize;
+        }
+
+    };
+
+    public static void main(String[] args) throws Exception {
+
+        TestCipherKeyWrapperTest test = new TestCipherKeyWrapperTest();
+        // AESWrap and DESedeWrap test
+        for (AlgorithmWrapper algoWrapper : AlgorithmWrapper.values()) {
+            String algo = algoWrapper.getAlgorithm();
+            String wrapper = algoWrapper.getWrapper();
+            try {
+                int keySize = algoWrapper.getKeySize();
+                // only run the tests on longer key lengths if unlimited
+                // version of JCE jurisdiction policy files are installed
+                if (!(Cipher.getMaxAllowedKeyLength(algo) == Integer.MAX_VALUE)
+                        && keySize > LINIMITED_KEYSIZE) {
+                    out.println(algo + " will not run if unlimited version of"
+                            + " JCE jurisdiction policy files are installed");
+                    continue;
+                }
+                test.wrapperAesDESedeKeyTest(algo, wrapper, keySize);
+                if (algoWrapper == AlgorithmWrapper.NegtiveWrap) {
+                    throw new RuntimeException("Expected not throw when algo"
+                            + " and wrapAlgo are not match:" + algo);
+                }
+            } catch (InvalidKeyException e) {
+                if (algoWrapper == AlgorithmWrapper.NegtiveWrap) {
+                    out.println("Expepted exception when algo"
+                            + " and wrapAlgo are not match:" + algo);
+                } else {
+                    throw e;
+                }
+            }
+        }
+        test.wrapperBlowfishKeyTest();
+        // PBE and public wrapper test.
+        String[] publicPrivateAlgos = new String[] { "DiffieHellman", "DSA",
+                "RSA" };
+        Provider provider = Security.getProvider(SUN_JCE);
+        if (provider == null) {
+            throw new RuntimeException("SUN_JCE provider not exist");
+        }
+
+        test.wrapperPBEKeyTest(provider);
+        // Public and private key wrap test
+        test.wrapperPublicPriviteKeyTest(provider, publicPrivateAlgos);
+    }
+
+    private void wrapperAesDESedeKeyTest(String algo, String wrapAlgo,
+            int keySize) throws InvalidKeyException, NoSuchAlgorithmException,
+            NoSuchPaddingException, IllegalBlockSizeException,
+            InvalidAlgorithmParameterException {
+        // Initialization
+        KeyGenerator kg = KeyGenerator.getInstance(algo);
+        if (keySize != -1) {
+            kg.init(keySize);
+        }
+        SecretKey key = kg.generateKey();
+        wrapTest(algo, wrapAlgo, key, key, Cipher.SECRET_KEY, false);
+    }
+
+    private void wrapperBlowfishKeyTest() throws InvalidKeyException,
+            NoSuchAlgorithmException, NoSuchPaddingException,
+            IllegalBlockSizeException, InvalidAlgorithmParameterException {
+        // how many kinds of padding mode
+        int padKinds;
+        // Keysize should be multiple of 8 bytes.
+        int KeyCutter = 8;
+        int kSize = BLOWFISH_MIN_KEYSIZE;
+        String algorithm = "Blowfish";
+        int maxAllowKeyLength = Cipher.getMaxAllowedKeyLength(algorithm);
+        boolean unLimitPolicy = maxAllowKeyLength == Integer.MAX_VALUE;
+        SecretKey key = null;
+        while (kSize <= BLOWFISH_MAX_KEYSIZE) {
+            for (String mode : MODEL_AR) {
+                // PKCS5padding is meaningful only for ECB, CBC, PCBC
+                if (mode.equalsIgnoreCase(MODEL_AR[0])
+                        || mode.equalsIgnoreCase(MODEL_AR[1])
+                        || mode.equalsIgnoreCase(MODEL_AR[2])) {
+                    padKinds = PADDING_AR.length;
+                } else {
+                    padKinds = 1;
+                }
+                // Initialization
+                KeyGenerator kg = KeyGenerator.getInstance(algorithm);
+                for (int k = 0; k < padKinds; k++) {
+                    String transformation = algorithm + "/" + mode + "/"
+                            + PADDING_AR[k];
+                    if (NOPADDING.equals(PADDING_AR[k]) && kSize % 64 != 0) {
+                        out.println(transformation
+                                + " will not run if input length not multiple"
+                                + " of 8 bytes when padding is " + NOPADDING);
+                        continue;
+                    }
+                    kg.init(kSize);
+                    key = kg.generateKey();
+                    // only run the tests on longer key lengths if unlimited
+                    // version of JCE jurisdiction policy files are installed
+                    if (!unLimitPolicy && kSize > LINIMITED_KEYSIZE) {
+                        out.println("keyStrength > 128 within " + algorithm
+                                + " will not run under global policy");
+                    } else {
+                        wrapTest(transformation, transformation, key, key,
+                                Cipher.SECRET_KEY, false);
+                    }
+                }
+            }
+            if (kSize <= LINIMITED_KEYSIZE) {
+                KeyCutter = 8;
+            } else {
+                KeyCutter = 48;
+            }
+            kSize += KeyCutter;
+        }
+    }
+
+    private void wrapperPBEKeyTest(Provider p) throws InvalidKeySpecException,
+            InvalidKeyException, NoSuchPaddingException,
+            IllegalBlockSizeException, InvalidAlgorithmParameterException,
+            NoSuchAlgorithmException {
+        for (String alg : PBE_ALGORITHM_AR) {
+            String baseAlgo = alg.split("/")[0].toUpperCase();
+            // only run the tests on longer key lengths if unlimited version
+            // of JCE jurisdiction policy files are installed
+
+            if (Cipher.getMaxAllowedKeyLength(alg) < Integer.MAX_VALUE
+                    && (baseAlgo.endsWith("TRIPLEDES") || alg
+                            .endsWith("AES_256"))) {
+                out.println("keyStrength > 128 within " + alg
+                        + " will not run under global policy");
+                continue;
+            }
+            SecretKeyFactory skf = SecretKeyFactory.getInstance(baseAlgo, p);
+            SecretKey key = skf.generateSecret(new PBEKeySpec("Secret Lover"
+                    .toCharArray()));
+            wrapTest(alg, alg, key, key, Cipher.SECRET_KEY, true);
+        }
+    }
+
+    private void wrapperPublicPriviteKeyTest(Provider p, String[] algorithms)
+            throws NoSuchAlgorithmException, InvalidKeyException,
+            NoSuchPaddingException, IllegalBlockSizeException,
+            InvalidAlgorithmParameterException {
+        for (String algo : algorithms) {
+            // Key pair generated
+            System.out.println("Generate key pair (algorithm: " + algo
+                    + ", provider: " + p.getName() + ")");
+            KeyPairGenerator kpg = KeyPairGenerator.getInstance(algo);
+            kpg.initialize(512);
+            KeyPair kp = kpg.genKeyPair();
+            // key generated
+            String algoWrap = "DES";
+            KeyGenerator kg = KeyGenerator.getInstance(algoWrap, p);
+            Key key = kg.generateKey();
+            wrapTest(algo, algoWrap, key, kp.getPrivate(), Cipher.PRIVATE_KEY,
+                    false);
+            wrapTest(algo, algoWrap, key, kp.getPublic(), Cipher.PUBLIC_KEY,
+                    false);
+        }
+    }
+
+    private void wrapTest(String transformation, String wrapAlgo, Key initKey,
+            Key wrapKey, int keyType, boolean isPBE)
+            throws NoSuchAlgorithmException, NoSuchPaddingException,
+            InvalidKeyException, IllegalBlockSizeException,
+            InvalidAlgorithmParameterException {
+        String algo = transformation.split("/")[0];
+        boolean isAESBlowfish = algo.indexOf("AES") != -1
+                || algo.indexOf("Blowfish") != -1;
+        AlgorithmParameters aps = null;
+        AlgorithmParameterSpec pbeParams = null;
+        if (isPBE) {
+            byte[] salt = new byte[8];
+            int iterCnt = 1000;
+            new Random().nextBytes(salt);
+            pbeParams = new PBEParameterSpec(salt, iterCnt);
+        }
+        // Wrap & UnWrap operation
+        Cipher wrapCI = Cipher.getInstance(wrapAlgo);
+        if (isPBE && !isAESBlowfish) {
+            wrapCI.init(Cipher.WRAP_MODE, initKey, pbeParams);
+        } else if (isAESBlowfish) {
+            wrapCI.init(Cipher.WRAP_MODE, initKey);
+            aps = wrapCI.getParameters();
+        } else {
+            wrapCI.init(Cipher.WRAP_MODE, initKey);
+        }
+        out.println("keysize : " + wrapKey.getEncoded().length);
+        byte[] keyWrapper = wrapCI.wrap(wrapKey);
+        if (isPBE && !isAESBlowfish) {
+            wrapCI.init(Cipher.UNWRAP_MODE, initKey, pbeParams);
+        } else if (isAESBlowfish) {
+            wrapCI.init(Cipher.UNWRAP_MODE, initKey, aps);
+        } else {
+            wrapCI.init(Cipher.UNWRAP_MODE, initKey);
+        }
+        Key unwrappedKey = wrapCI.unwrap(keyWrapper, algo, keyType);
+        // Comparison
+        if (!Arrays.equals(wrapKey.getEncoded(), unwrappedKey.getEncoded())) {
+            throw new RuntimeException("Comparation failed testing "
+                    + transformation + ":" + wrapAlgo + ":" + keyType);
+        }
+    }
+}
--- a/jdk/test/com/sun/jdi/BadHandshakeTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/com/sun/jdi/BadHandshakeTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -84,14 +84,19 @@
             class_name,
             pb,
             (line) -> {
-                // The first thing that will get read is
-                //    Listening for transport dt_socket at address: xxxxx
-                // which shows the debuggee is ready to accept connections.
-                success.set(line.contains("Listening for transport dt_socket at address:"));
-                // If the first line contains 'Address already in use'
-                // that means the debuggee has failed to start due to busy port
-                bindFailed.set(line.contains("Address already in use"));
-                return true;
+                // 'Listening for transport dt_socket at address: xxxxx'
+                // indicates the debuggee is ready to accept connections
+                if (line.contains("Listening for transport dt_socket at address:")) {
+                    success.set(true);
+                    return true;
+                }
+                // 'Address already in use' indicates
+                // the debuggee has failed to start due to busy port.
+                if (line.contains("Address already in use")) {
+                    bindFailed.set(true);
+                    return true;
+                }
+                return false;
             },
             Integer.MAX_VALUE,
             TimeUnit.MILLISECONDS
--- a/jdk/test/com/sun/jdi/NoLaunchOptionTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/com/sun/jdi/NoLaunchOptionTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,134 +21,35 @@
  * questions.
  */
 
-/*
- *   @test       NoLaunchOptionTest.java
- *   @bug        4554734 4724714
- *   @summary    Test for -Xrunjdwp:[onthrow,onuncaught] suboptions require launch suboption
- *   @author     Tim Bell
- *
- *  @modules jdk.jdi
- *  @run compile -g NoLaunchOptionTest.java
- *  @build VMConnection
- *  @run driver NoLaunchOptionTest
- */
-
-import java.net.ServerSocket;
-
-public class NoLaunchOptionTest extends Object {
-    private Process subprocess;
-    private int subprocessStatus;
-    private static final String CR = System.getProperty("line.separator");
-    private static final int BUFFERSIZE = 4096;
-    public static final int RETSTAT = 0;
-    public static final int STDOUT = 1;
-    public static final int STDERR = 2;
-
-    /**
-     * Run an arbitrary command and return the results to caller.
-     *
-     * @param an array of String containing the command
-     *        to run and any flags or parameters to the command.
-     *
-     * @return completion status, stderr and stdout as array of String
-     *  Look for:
-     *    return status in result[NoLaunchOptionTest.RETSTAT]
-     *    standard out in result[NoLaunchOptionTest.STDOUT]
-     *    standard err in result[NoLaunchOptionTest.STDERR]
-     *
-     */
-    public String[] run (String[] cmdStrings) {
-        StringBuffer stdoutBuffer = new StringBuffer();
-        StringBuffer stderrBuffer = new StringBuffer();
+import static jdk.testlibrary.Asserts.assertFalse;
+import jdk.testlibrary.OutputAnalyzer;
+import jdk.testlibrary.ProcessTools;
 
-        System.out.print(CR + "runCommand method about to execute: ");
-        for (int iNdx = 0; iNdx < cmdStrings.length; iNdx++) {
-            System.out.print(" ");
-            System.out.print(cmdStrings[iNdx]);
-        }
-        System.out.println(CR);
-        try {
-            Process process = Runtime.getRuntime().exec(cmdStrings);
-            /*
-             * Gather up the output of the subprocess using non-blocking
-             * reads so we can get both the subprocess stdout and the
-             * subprocess stderr without overfilling any buffers.
-             */
-            java.io.BufferedInputStream is =
-                new java.io.BufferedInputStream(process.getInputStream());
-            int isLen = 0;
-            byte[] isBuf = new byte[BUFFERSIZE];
-
-            java.io.BufferedInputStream es =
-                new java.io.BufferedInputStream(process.getErrorStream());
-            int esLen = 0;
-            byte[] esBuf = new byte[BUFFERSIZE];
-
-            do {
-                isLen = is.read(isBuf);
-                if (isLen > 0) {
-                    stdoutBuffer.append(
-                                        new String(isBuf, 0, isLen));
-                }
-                esLen = es.read(esBuf);
-                if (esLen > 0) {
-                    stderrBuffer.append(
-                                        new String(esBuf, 0, esLen));
-                }
-            } while ((isLen > -1) || (esLen > -1));
-            try {
-                process.waitFor();
-                subprocessStatus = process.exitValue();
-                process = null;
-            } catch(java.lang.InterruptedException e) {
-                System.err.println("InterruptedException: " + e);
-            }
-
-        } catch(java.io.IOException ex) {
-            System.err.println("IO error: " + ex);
-        }
-        String[] result =
-            new String[] {
-                Integer.toString(subprocessStatus),
-                stdoutBuffer.toString(),
-                stderrBuffer.toString()
-        };
-
-        System.out.println(CR + "--- Return code was: " +
-                           CR + result[RETSTAT]);
-        System.out.println(CR + "--- Return stdout was: " +
-                           CR + result[STDOUT]);
-        System.out.println(CR + "--- Return stderr was: " +
-                           CR + result[STDERR]);
-
-        return result;
-    }
+/*
+ * @test       NoLaunchOptionTest.java
+ * @bug        4554734 4724714
+ * @summary    Test for -Xrunjdwp:[onthrow,onuncaught] suboptions require launch suboption
+ * @author     Tim Bell
+ * @library /lib/testlibrary
+ * @modules jdk.jdi
+ * @run compile -g NoLaunchOptionTest.java
+ * @build jdk.testlibrary.* VMConnection
+ * @run driver NoLaunchOptionTest
+ */
+public class NoLaunchOptionTest extends Object {
 
     public static void main(String[] args) throws Exception {
-        // find a free port
-        ServerSocket ss = new ServerSocket(0);
-        int port = ss.getLocalPort();
-        ss.close();
-        String address = String.valueOf(port);
+        String[] cmd = VMConnection.insertDebuggeeVMOptions(new String[] {
+                "-agentlib:jdwp=transport=dt_socket,address=5555," +
+                "onthrow=java.lang.ClassNotFoundException,suspend=n",
+                "NotAClass" });
 
-        String javaExe = System.getProperty("java.home") +
-            java.io.File.separator + "bin" +
-            java.io.File.separator + "java";
-        String targetClass = "NotAClass";
-        String cmds [] = {javaExe,
-                          "-agentlib:jdwp=transport=dt_socket,address=" +
-                          address + "," +
-                          "onthrow=java.lang.ClassNotFoundException,suspend=n",
-                          targetClass};
-        NoLaunchOptionTest myTest = new NoLaunchOptionTest();
-        String results [] = myTest.run(VMConnection.insertDebuggeeVMOptions(cmds));
-        if ((results[RETSTAT].equals("1")) &&
-            (results[STDERR].contains("ERROR:"))) {
-            System.out.println("Test passed: status = 1 with warning messages " +
-                               "is expected and normal for this test");
-        } else {
-            throw new Exception("Test failed: unspecified test failure");
-        }
+        ProcessBuilder pb = ProcessTools.createJavaProcessBuilder(cmd);
+        OutputAnalyzer output = ProcessTools.executeProcess(pb);
+        System.out.println(output.getOutput());
+
+        assertFalse(output.getExitValue() == 0, "Exit code should not be 0");
+        output.shouldContain("ERROR: JDWP Specify launch=<command line> when using onthrow or onuncaught suboption");
     }
 
 }
--- a/jdk/test/com/sun/management/HotSpotDiagnosticMXBean/DumpHeap.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/com/sun/management/HotSpotDiagnosticMXBean/DumpHeap.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2006, 2008, 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
@@ -21,22 +21,55 @@
  * questions.
  */
 
-/*
- *
- * @bug 6455258
- * @summary Sanity test for com.sun.management.HotSpotDiagnosticMXBean.dumpHeap
- *          method
- */
+import static jdk.testlibrary.Asserts.assertTrue;
+import static jdk.testlibrary.Asserts.fail;
 
+import java.io.File;
 import java.lang.management.*;
 import java.util.List;
-import javax.management.MBeanServer;
+
+import jdk.test.lib.hprof.HprofParser;
+import jdk.testlibrary.ProcessTools;
+
 import com.sun.management.HotSpotDiagnosticMXBean;
 
+/*
+ * @test
+ * @bug 6455258
+ * @summary Sanity test for com.sun.management.HotSpotDiagnosticMXBean.dumpHeap method
+ * @library /lib/testlibrary
+ * @library /../../test/lib/share/classes
+ * @build jdk.testlibrary.*
+ * @build jdk.test.lib.hprof.*
+ * @build jdk.test.lib.hprof.module.*
+ * @build jdk.test.lib.hprof.parser.*
+ * @build jdk.test.lib.hprof.utils.*
+ * @run main DumpHeap
+ */
 public class DumpHeap {
-    public static void main(String[] argv) throws Exception {
-         List<HotSpotDiagnosticMXBean> list = ManagementFactory.getPlatformMXBeans(HotSpotDiagnosticMXBean.class);
-         System.out.println("Dumping to file: " + argv[0] + " ....");
-         list.get(0).dumpHeap(argv[0], true);
+
+    public static void main(String[] args) throws Exception {
+        List<HotSpotDiagnosticMXBean> list = ManagementFactory.getPlatformMXBeans(HotSpotDiagnosticMXBean.class);
+        File dump = new File(ProcessTools.getProcessId() + ".hprof");
+        if (dump.exists()) {
+            dump.delete();
+        }
+        System.out.println("Dumping to file: " + dump.getAbsolutePath());
+        list.get(0).dumpHeap(dump.getAbsolutePath(), true);
+
+        verifyDumpFile(dump);
+
+        dump.delete();
     }
+
+    private static void verifyDumpFile(File dump) {
+        assertTrue(dump.exists() && dump.isFile(), "Could not create dump file");
+        try {
+            HprofParser.parse(dump);
+        } catch (Exception e) {
+            e.printStackTrace();
+            fail("Could not parse dump file");
+        }
+    }
+
 }
--- a/jdk/test/com/sun/management/HotSpotDiagnosticMXBean/DumpHeap.sh	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,60 +0,0 @@
-#!/bin/sh
-
-#
-# 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 6455258
-# @summary Sanity test for com.sun.management.HotSpotDiagnosticMXBean.dumpHeap 
-#          method 
-#
-# @modules jdk.management
-# @build DumpHeap
-# @run shell DumpHeap.sh
-
-if [ "${TESTJAVA}" = "" ] ; then
-     echo "--Error: TESTJAVA must be defined as the pathname of a jdk to test."
-     exit 1
-fi
-
-if [ "${COMPILEJAVA}" = "" ] ; then
-    COMPILEJAVA="${TESTJAVA}"
-fi
-
-failed=0
-
-# we use the pid of this shell process to name the heap dump output file.
-DUMPFILE="java_pid$$.hprof"
-
-${TESTJAVA}/bin/java ${TESTVMOPTS} -classpath $TESTCLASSES \
-    DumpHeap ${DUMPFILE} || exit 2
-
-# check that heap dump is parsable
-${COMPILEJAVA}/bin/jhat ${TESTTOOLVMOPTS} -parseonly true ${DUMPFILE}
-if [ $? != 0 ]; then failed=1; fi
-
-# dump file is large so remove it
-rm ${DUMPFILE}
-
-exit $failed
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/lang/Character/UnicodeBlock/NonOptimalMapSize.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,72 @@
+/*
+ * 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 8080535
+ * @summary Expected size of Character.UnicodeBlock.map is not optimal
+ */
+
+import java.lang.reflect.Field;
+import java.util.HashMap;
+import java.util.Map;
+
+public class NonOptimalMapSize {
+    public static void main(String[] args) throws Throwable {
+        Class<?> ubCls = Character.UnicodeBlock.class;
+        Field mapField = ubCls.getDeclaredField("map");
+        mapField.setAccessible(true);
+        Map<?,?> map = (Map<?,?>)mapField.get(null);
+        if (!map.getClass().equals(HashMap.class)) {
+            throw new RuntimeException(
+                    "Character.UnicodeBlock.map is expected to be HashMap");
+        }
+        int mapSize = map.size();
+
+        Field sizeField = ubCls.getDeclaredField("INITIAL_CAPACITY");
+        sizeField.setAccessible(true);
+        int INITIAL_CAPACITY = sizeField.getInt(null);
+
+        // Construct a HashMap with specified initial capacity
+        HashMap<Object,Object> map1 = new HashMap<>(INITIAL_CAPACITY);
+        Class<?> hmCls = HashMap.class;
+        Field tableField = hmCls.getDeclaredField("table");
+        tableField.setAccessible(true);
+        // ... and fill it up
+        map1.put(new Object(), new Object());
+        final Object initialTable = tableField.get(map1);
+        while (map1.size() < map.size() &&
+                initialTable == tableField.get(map1)) {
+            map1.put(new Object(), new Object());
+        }
+
+        // Now check that internal storage didn't change
+        if (initialTable != tableField.get(map1)) {
+            throw new RuntimeException(
+                    "Initial capacity " + INITIAL_CAPACITY +
+                    " was only enough to hold " + (map1.size()-1) +
+                    " entries, but needed " + map.size());
+        }
+    }
+}
--- a/jdk/test/java/lang/Runtime/exec/LotsOfOutput.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/java/lang/Runtime/exec/LotsOfOutput.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2002, 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
@@ -23,12 +23,22 @@
 
 /**
  * @test
- * @bug 4369826
+ * @bug 4369826 8078582
  * @summary Process with lots of output should not crash VM
+ * @key intermittent
  * @author kladko
  */
 
 public class LotsOfOutput {
+    static final Runtime runtime = Runtime.getRuntime();
+
+    // Allow memory to grow by up to 1Mb total
+    static final int THRESHOLD = 1048576;
+
+    // Compute used memory
+    static long usedMemory() {
+        return runtime.totalMemory() - runtime.freeMemory();
+    }
 
     public static void main(String[] args) throws Exception {
         if (! UnixCommands.isUnix) {
@@ -37,18 +47,21 @@
         }
         UnixCommands.ensureCommandsAvailable("cat");
 
-        Process p = Runtime.getRuntime().exec(UnixCommands.cat() + " /dev/zero");
-        long initMemory = Runtime.getRuntime().totalMemory();
-        for (int i=1; i< 10; i++) {
+        Process p = runtime.exec(UnixCommands.cat() + " /dev/zero");
+        long initMemory = usedMemory();
+        boolean growing = false;
+        for (int i = 1; i < 10; i++) {
             Thread.sleep(100);
-            long totalMemory = Runtime.getRuntime().totalMemory();
-            if (totalMemory != initMemory) {
-                System.out.printf("consuming memory: i: %d, initial: %d, total: %d, delta: %d%n",
-                        i, initMemory, totalMemory, totalMemory - initMemory);
+            long used = usedMemory();
+            if (used != initMemory) {
+                System.out.printf("consuming memory: i: %d, initial: %d, used: %d, delta: %d%n",
+                        i, initMemory, used, used - initMemory);
             }
-            if (totalMemory > initMemory + 1000000)
-                throw new Exception("Process consumes memory.");
+            if (used > initMemory + THRESHOLD)
+                growing = true;
         }
+        if (growing)
+            throw new Exception("Process consumes memory.");
 
     }
 }
--- a/jdk/test/java/lang/invoke/MethodHandles/CatchExceptionTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/java/lang/invoke/MethodHandles/CatchExceptionTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -72,12 +72,6 @@
             final int catchDrops) {
         this.testCase = testCase;
         this.dropped = catchDrops;
-        if (Helper.IS_VERBOSE) {
-            System.out.printf("CatchException::CatchException(%s, isVararg=%b " +
-                            "argsCount=%d catchDrops=%d)%n",
-                    testCase, isVararg, argsCount, catchDrops
-            );
-        }
         MethodHandle thrower = testCase.thrower;
         int throwerLen = thrower.type().parameterCount();
         List<Class<?>> classes;
@@ -97,9 +91,11 @@
     }
 
     public static void main(String[] args) throws Throwable {
+        System.out.println("classes = " + ARGS_CLASSES);
+
         TestFactory factory = new TestFactory();
         long timeout = Helper.IS_THOROUGH ? 0L : Utils.adjustTimeout(Utils.DEFAULT_TEST_TIMEOUT);
-        // substract vm init time and reserve time for vm exit
+        // subtract vm init time and reserve time for vm exit
         timeout *= 0.9;
         TimeLimitedRunner runner = new TimeLimitedRunner(timeout, 2.0d,
                 () -> {
@@ -131,6 +127,12 @@
     }
 
     private void runTest() {
+        if (Helper.IS_VERBOSE) {
+            System.out.printf("CatchException(%s, isVararg=%b argsCount=%d " +
+                            "dropped=%d)%n",
+                    testCase, thrower.isVarargsCollector(), argsCount, dropped);
+        }
+
         Helper.clear();
 
         Object[] args = Helper.randomArgs(
@@ -212,10 +214,7 @@
             args = 1;
         }
 
-        if (Helper.IS_VERBOSE) {
-            System.out.printf("maxArgs = %d%nmaxDrops = %d%n",
-                    maxArgs, maxDrops);
-        }
+        System.out.printf("maxArgs = %d%nmaxDrops = %d%n", maxArgs, maxDrops);
         constructorSize = TestCase.CONSTRUCTORS.size();
     }
 
@@ -243,7 +242,7 @@
 
     /**
      * @return next test from test matrix:
-     * {varArgs, noVarArgs} x TestCase.rtypes x TestCase.THROWABLES x {1, .., maxArgs } x {1, .., maxDrops}
+     * {varArgs, noVarArgs} x TestCase.rtypes x TestCase.THROWABLES x {1, .., maxArgs } x {0, .., maxDrops}
      */
     public CatchExceptionTest nextTest() {
         if (constructor < constructorSize) {
@@ -256,7 +255,7 @@
             return null;
         }
         if (dropArgs <= currentMaxDrops) {
-            if (dropArgs == 1) {
+            if (dropArgs == 0) {
                 if (Helper.IS_THOROUGH || Helper.RNG.nextBoolean()) {
                     ++dropArgs;
                     return createTest();
@@ -271,8 +270,8 @@
             }
         }
 
-        if (args <= maxArgs) {
-            dropArgs = 1;
+        if (args < maxArgs) {
+            dropArgs = 0;
             currentMaxDrops = Math.min(args, maxDrops);
             ++args;
             return createTest();
--- a/jdk/test/java/nio/file/Files/SBC.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/java/nio/file/Files/SBC.java	Wed Jul 05 20:35:10 2017 +0200
@@ -22,7 +22,7 @@
  */
 
 /* @test
- * @bug 4313887 8066915
+ * @bug 4313887
  * @summary Unit test for java.nio.file.Files.newByteChannel
  * @library ..
  */
@@ -59,7 +59,6 @@
                 dosSharingOptionTests(dir);
 
             // misc. tests
-            directoryOpenTests(dir);
             badCombinations(dir);
             unsupportedOptions(dir);
             nullTests(dir);
@@ -279,21 +278,6 @@
         }
     }
 
-    // test opening a directory for read or write
-    static void directoryOpenTests(Path dir) throws Exception {
-        try (SeekableByteChannel sbc = Files.newByteChannel(dir, READ)) {
-            throw new RuntimeException("Opened directory for read");
-        } catch (IOException expected) { }
-
-        try (SeekableByteChannel sbc = Files.newByteChannel(dir, WRITE)) {
-            throw new RuntimeException("Opened directory for write");
-        } catch (IOException expected) { }
-
-        try (SeekableByteChannel sbc = Files.newByteChannel(dir, APPEND)) {
-            throw new RuntimeException("Opened directory for append ");
-        } catch (IOException expected) { }
-    }
-
     // Windows specific options for the use by applications that really want
     // to use legacy DOS sharing options
     static void dosSharingOptionTests(Path dir) throws Exception {
--- a/jdk/test/java/security/KeyStore/ProbeKeystores.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/java/security/KeyStore/ProbeKeystores.java	Wed Jul 05 20:35:10 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
@@ -41,15 +41,6 @@
     private static final String CERT_FILE = "trusted.pem";
 
     public static final void main(String[] args) throws Exception {
-        try {
-            test();
-        } finally {
-            cleanup();
-        }
-    }
-
-    private static final void test() throws Exception {
-        cleanup();
 
         // Testing empty keystores
 
@@ -129,22 +120,11 @@
         System.out.println("OK.");
     }
 
-    private static void cleanup() {
-        new File("empty.jks").delete();
-        new File("empty.jceks").delete();
-        new File("empty.p12").delete();
-        new File("onecert.jks").delete();
-        new File("onecert.jceks").delete();
-        new File("onecert.p12").delete();
-        new File("onekey.jceks").delete();
-        new File("onekey.p12").delete();
-    }
-
     // Instantiate an empty keystore using the supplied keystore type
     private static void init(String file, String type) throws Exception {
         KeyStore ks = KeyStore.getInstance(type);
         ks.load(null, null);
-        try (OutputStream stream = new FileOutputStream(DIR + "/" + file)) {
+        try (OutputStream stream = new FileOutputStream(file)) {
             ks.store(stream, PASSWORD);
         }
         System.out.println("Created a " + type + " keystore named '" + file + "'");
@@ -156,7 +136,7 @@
         KeyStore ks = KeyStore.getInstance(type);
         ks.load(null, null);
         ks.setEntry("mycert", new KeyStore.TrustedCertificateEntry(cert), null);
-        try (OutputStream stream = new FileOutputStream(DIR + "/" + file)) {
+        try (OutputStream stream = new FileOutputStream(file)) {
             ks.store(stream, PASSWORD);
         }
         System.out.println("Created a " + type + " keystore named '" + file + "'");
@@ -169,7 +149,7 @@
         ks.load(null, null);
         ks.setEntry("mykey", new KeyStore.SecretKeyEntry(key),
             new PasswordProtection(PASSWORD));
-        try (OutputStream stream = new FileOutputStream(DIR + "/" + file)) {
+        try (OutputStream stream = new FileOutputStream(file)) {
             ks.store(stream, PASSWORD);
         }
         System.out.println("Created a " + type + " keystore named '" + file + "'");
@@ -178,7 +158,7 @@
     // Instantiate a keystore by probing the supplied file for the keystore type
     private static void probe(String file, String type) throws Exception {
         // First try with the correct password
-        KeyStore ks = KeyStore.getInstance(new File(DIR, file), PASSWORD);
+        KeyStore ks = KeyStore.getInstance(new File(file), PASSWORD);
         if (!type.equalsIgnoreCase(ks.getType())) {
             throw new Exception("ERROR: expected a " + type + " keystore, " +
                 "got a " + ks.getType() + " keystore instead");
@@ -188,7 +168,7 @@
 
         // Next try with an incorrect password
         try {
-            ks = KeyStore.getInstance(new File(DIR, file), BAD_PASSWORD);
+            ks = KeyStore.getInstance(new File(file), BAD_PASSWORD);
             throw new Exception("ERROR: expected an exception but got success");
         } catch (IOException e) {
             System.out.println("Failed to load a " + type + " keystore named '" + file + "' (as expected)");
@@ -201,10 +181,10 @@
 
         Builder builder;
         if (usePassword) {
-            builder = Builder.newInstance(new File(DIR, file),
+            builder = Builder.newInstance(new File(file),
                 new PasswordProtection(PASSWORD));
         } else {
-            builder = Builder.newInstance(new File(DIR, file),
+            builder = Builder.newInstance(new File(file),
                 new CallbackHandlerProtection(new DummyHandler()));
         }
         KeyStore ks = builder.getKeyStore();
@@ -219,7 +199,7 @@
     // Load the keystore entries
     private static void load(String file, String type) throws Exception {
         KeyStore ks = KeyStore.getInstance(type);
-        try (InputStream stream = new FileInputStream(DIR + "/" + file)) {
+        try (InputStream stream = new FileInputStream(file)) {
             ks.load(stream, PASSWORD);
         }
         if (!type.equalsIgnoreCase(ks.getType())) {
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/util/logging/LogManager/Configuration/TestConfigurationLock.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,457 @@
+/*
+ * 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.File;
+import java.io.IOException;
+import java.lang.management.LockInfo;
+import java.lang.management.ManagementFactory;
+import java.lang.management.MonitorInfo;
+import java.lang.management.ThreadInfo;
+import java.security.Permission;
+import java.security.Policy;
+import java.security.ProtectionDomain;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.concurrent.atomic.AtomicLong;
+import java.util.logging.Level;
+import java.util.logging.LogManager;
+import java.util.logging.Logger;
+
+
+/**
+ * @test
+ * @bug 8077846
+ * @key randomness
+ * @summary Test that using a reentrant configuration lock does not introduce
+ *       new synchronization issues in Logger and LogManager. This test
+ *       focuses more particularly on potential deadlock in
+ *       drainLoggerRefQueueBounded / readConfiguration / reset
+ *       todo: add at randomness
+ * @run main/othervm TestConfigurationLock
+ * @author danielfuchs
+ */
+// This test is a best effort to try & detect issues. The test itself will run
+// for 8secs. This might be unsufficient to detect issues.
+// To get a greater confidence it is recommended to run this test in a loop:
+// e.g. use something like:
+// $ while jtreg -jdk:$JDK -verbose:all  \
+//      test/java/util/logging/TestConfigurationLock.java ; \
+//      do echo Running test again ; done
+// and let it run for a few hours...
+//
+public class TestConfigurationLock {
+
+    static volatile Exception thrown = null;
+    static volatile boolean goOn = true;
+    static volatile boolean deadlock = false;
+
+    static final double CONFSYNCTHRESHOLD = 0.3;
+    static final double LOGSYNCTHRESHOLD = 0.3;
+    static final int RESETERS = 0;
+    static final int READERS = 3;
+    static final int LOGGERS = 4;
+    static final long TIME = 8 * 1000; // 8 sec.
+    static final long STEP = 1 * 1000;  // message every 1 sec.
+    static final int  LCOUNT = 50; // 50 loggers created in a row...
+    static final AtomicLong nextLogger = new AtomicLong(0);
+    static final AtomicLong resetCount = new AtomicLong(0);
+    static final AtomicLong readCount = new AtomicLong(0);
+    static final AtomicLong checkCount = new AtomicLong(0);
+
+    static final String BLAH = "blah";
+
+    static Object fakeConfExternalLock() {
+        return LogManager.getLogManager();
+    }
+
+    static Object fakeLogExternalLock() {
+        return LogManager.getLogManager();
+    }
+
+
+     /**
+     * This test will run both with and without a security manager.
+     *
+     * The test starts a number of threads that will call
+     *     LogManager.reset() concurrently (ResetConf), and a number of threads
+     *     that will call readConfiguration() (ReadConf), and then starts a
+     *     number of threads that will create new loggers concurrently
+     *     (AddLogger), and finally two additional threads:
+     *     - one (Stopper) that will stop the test after 4secs (TIME ms),
+     *     - and one DeadlockDetector that will attempt to detect deadlocks.
+     * If after 4secs no deadlock was detected and no exception was thrown
+     * then the test is considered a success and passes.
+     *
+     * This procedure is done twice: once without a security manager and once
+     * again with a security manager - which means the test takes ~8secs to
+     * run.
+     *
+     * Note that 8sec may not be enough to detect issues if there are some.
+     * This is a best effort test.
+     *
+     * @param args the command line arguments
+     * @throws java.lang.Exception if the test fails
+     */
+    public static void main(String[] args) throws Exception {
+
+        File conf = new File(System.getProperty("test.src", "./src"),
+                TestConfigurationLock.class.getSimpleName() + ".properties");
+        if (!conf.canRead()) {
+            throw new IOException("Can't read config file: " + conf.getAbsolutePath());
+        }
+        System.setProperty("java.util.logging.config.file", conf.getAbsolutePath());
+        // test without security
+        System.out.println("No security");
+        test();
+
+        // test with security
+        System.out.println("\nWith security");
+        Policy.setPolicy(new Policy() {
+            @Override
+            public boolean implies(ProtectionDomain domain, Permission permission) {
+                if (super.implies(domain, permission)) return true;
+                // System.out.println("Granting " + permission);
+                return true; // all permissions
+            }
+        });
+        System.setSecurityManager(new SecurityManager());
+        test();
+    }
+
+
+    /**
+     * Starts all threads, wait 4secs, then stops all threads.
+     * @throws Exception if a deadlock was detected or an error occurred.
+     */
+    public static void test() throws Exception {
+          goOn = true;
+          thrown = null;
+          long sNextLogger = nextLogger.get();
+          long sUpdateCount  = resetCount.get();
+          long sReadCount  = readCount.get();
+          long sCheckCount = checkCount.get();
+          List<Thread> threads = new ArrayList<>();
+          for (int i = 0; i<RESETERS; i++) {
+              threads.add(new ResetConf());
+          }
+          for (int i = 0; i<READERS; i++) {
+              threads.add(new ReadConf());
+          }
+          for (int i = 0; i<LOGGERS; i++) {
+              threads.add(new AddLogger());
+          }
+          threads.add(0, new Stopper(TIME));
+          threads.stream().forEach(Thread::start);
+
+          Thread deadLockDetector = new DeadlockDetector();
+          deadLockDetector.start();
+          deadLockDetector.join();
+
+          if (!deadlock) {
+              threads.stream().forEach(TestConfigurationLock::join);
+          } else {
+              System.err.println("Deadlock found: exiting forcibly.");
+              Runtime.getRuntime().halt(-1);
+          }
+
+          if (thrown != null) {
+              throw thrown;
+          }
+          System.out.println("Passed: " + (nextLogger.get() - sNextLogger)
+                  + " loggers created by " + LOGGERS + " Thread(s),");
+          System.out.println("\t LogManager.reset() called "
+                  + (resetCount.get() - sUpdateCount) + " times by " + RESETERS
+                  + " Thread(s).");
+          System.out.println("\t LogManager.readConfiguration() called "
+                  + (readCount.get() - sReadCount) + " times by " + READERS
+                  + " Thread(s).");
+          System.out.println("\t ThreadMXBean.findDeadlockedThreads called "
+                  + (checkCount.get() -sCheckCount) + " times by 1 Thread.");
+
+    }
+
+    static void join(Thread t) {
+        try {
+            t.join();
+        } catch (Exception x) {
+            fail(x);
+        }
+    }
+
+    final static class ResetConf extends Thread {
+
+        public ResetConf() {
+            setDaemon(true);
+        }
+
+        @Override
+        public void run() {
+            while (goOn) {
+                try {
+                    if (Math.random() > CONFSYNCTHRESHOLD) {
+                        // calling reset while holding a lock can increase
+                        // deadlock probability...
+                        synchronized(fakeConfExternalLock()) {
+                            LogManager.getLogManager().reset();
+                        }
+                    } else {
+                        LogManager.getLogManager().reset();
+                    }
+                    Logger blah = Logger.getLogger(BLAH);
+                    blah.setLevel(Level.FINEST);
+                    blah.fine(BLAH);
+                    resetCount.incrementAndGet();
+                    pause(1);
+                } catch (Exception x) {
+                    fail(x);
+                }
+            }
+        }
+    }
+
+    final static class ReadConf extends Thread {
+
+        public ReadConf() {
+            setDaemon(true);
+        }
+
+        @Override
+        public void run() {
+            while (goOn) {
+                try {
+                    if (Math.random() > CONFSYNCTHRESHOLD) {
+                        // calling readConfiguration while holding a lock can
+                        // increase deadlock probability...
+                        synchronized(fakeConfExternalLock()) {
+                            LogManager.getLogManager().readConfiguration();
+                        }
+                    } else {
+                        LogManager.getLogManager().readConfiguration();
+                    }
+                    Logger blah = Logger.getLogger(BLAH);
+                    blah.setLevel(Level.FINEST);
+                    blah.fine(BLAH);
+                    readCount.incrementAndGet();
+                    pause(1);
+                } catch (Exception x) {
+                    fail(x);
+                }
+            }
+        }
+    }
+
+    final static class AddLogger extends Thread {
+
+        public AddLogger() {
+            setDaemon(true);
+        }
+
+        @Override
+        public void run() {
+            try {
+                while (goOn) {
+                    Logger l;
+                    Logger foo = Logger.getLogger("foo");
+                    Logger bar = Logger.getLogger("foo.bar");
+                    for (int i=0; i < LCOUNT ; i++) {
+                        LogManager manager = LogManager.getLogManager();
+                        if (Math.random() > LOGSYNCTHRESHOLD) {
+                            synchronized(fakeLogExternalLock()) {
+                                l = Logger.getLogger("foo.bar.l"+nextLogger.incrementAndGet());
+                            }
+                        } else {
+                            l = Logger.getLogger("foo.bar.l"+nextLogger.incrementAndGet());
+                        }
+                        l.setLevel(Level.FINEST);
+                        l.fine("I'm fine");
+                        if (!goOn) break;
+                        pause(1);
+                    }
+                }
+            } catch (InterruptedException | RuntimeException x ) {
+                fail(x);
+            }
+        }
+    }
+
+    final static class DeadlockDetector extends Thread {
+
+        @Override
+        public void run() {
+            boolean deadlock = false;
+            while(goOn) {
+                try {
+                    long[] ids = ManagementFactory.getThreadMXBean().findDeadlockedThreads();
+                    checkCount.incrementAndGet();
+                    ids = ids == null ? new long[0] : ids;
+                    if (ids.length == 1) {
+                        throw new RuntimeException("Found 1 deadlocked thread: "+ids[0]);
+                    } else if (ids.length > 0) {
+                        deadlock = true;
+                        ThreadInfo[] infos = ManagementFactory.getThreadMXBean()
+                            .getThreadInfo(ids, true, true);
+                        System.err.println("Found "+ids.length+" deadlocked threads: ");
+                        for (ThreadInfo inf : infos) {
+                            System.err.println(asString(inf));
+                        }
+                        throw new RuntimeException("Found "+ids.length+" deadlocked threads");
+                    }
+                    pause(100);
+                } catch(InterruptedException | RuntimeException x) {
+                    if (deadlock) deadlock(x);
+                    else fail(x);
+                }
+            }
+        }
+
+    }
+
+    static final class Stopper extends Thread {
+        long start;
+        long time;
+
+        Stopper(long time) {
+            start = System.currentTimeMillis();
+            this.time = time;
+            setDaemon(true);
+        }
+
+        @Override
+        public void run() {
+            try {
+                long rest, previous;
+                int msgCount = 0;
+                previous = time;
+                Logger logger =  Logger.getLogger("remaining");
+                while (goOn && (rest = start - System.currentTimeMillis() + time) > 0) {
+                    if (previous == time || previous - rest >= STEP) {
+                        logger.log(Level.INFO, "{0}ms remaining...", String.valueOf(rest));
+                        msgCount++;
+                        previous = rest == time ? rest -1 : rest;
+                        System.gc();
+                    }
+                    if (goOn == false) break;
+                    pause(Math.min(rest, 100));
+                }
+                System.err.println(this + ": " + msgCount + " messages.");
+                System.err.flush();
+                System.out.println(System.currentTimeMillis() - start
+                        + " ms elapsed ("+time+ " requested)");
+                goOn = false;
+            } catch(InterruptedException | RuntimeException x) {
+                fail(x);
+            }
+        }
+
+    }
+
+    // ThreadInfo.toString() only prints 8 frames...
+    static String asString(ThreadInfo inf) {
+        StringBuilder sb = new StringBuilder();
+        sb.append("\"").append(inf.getThreadName()).append("\"")
+                .append(inf.isDaemon() ? " daemon" : "")
+                .append(" prio=").append(inf.getPriority())
+                .append(" Id=").append(inf.getThreadId())
+                .append(" ").append(inf.getThreadState());
+        if (inf.getLockName() != null) {
+            sb.append(" on ").append(inf.getLockName());
+        }
+        if (inf.getLockOwnerName() != null) {
+            sb.append(" owned by \"").append(inf.getLockOwnerName())
+                    .append("\" Id=").append(inf.getLockOwnerId());
+        }
+        if (inf.isSuspended()) {
+            sb.append(" (suspended)");
+        }
+        if (inf.isInNative()) {
+            sb.append(" (in native)");
+        }
+        sb.append('\n');
+        int i = 0;
+        StackTraceElement[] stackTrace = inf.getStackTrace();
+        for (; i < stackTrace.length; i++) {
+            StackTraceElement ste = stackTrace[i];
+            sb.append("\tat ").append(ste.toString());
+            sb.append('\n');
+            if (i == 0 && inf.getLockInfo() != null) {
+                Thread.State ts = inf.getThreadState();
+                switch (ts) {
+                    case BLOCKED:
+                        sb.append("\t-  blocked on ").append(inf.getLockInfo());
+                        sb.append('\n');
+                        break;
+                    case WAITING:
+                        sb.append("\t-  waiting on ").append(inf.getLockInfo());
+                        sb.append('\n');
+                        break;
+                    case TIMED_WAITING:
+                        sb.append("\t-  waiting on ").append(inf.getLockInfo());
+                        sb.append('\n');
+                        break;
+                    default:
+                }
+            }
+
+            for (MonitorInfo mi : inf.getLockedMonitors()) {
+                if (mi.getLockedStackDepth() == i) {
+                    sb.append("\t-  locked ").append(mi);
+                    sb.append('\n');
+                }
+            }
+        }
+        if (i < stackTrace.length) {
+           sb.append("\t...");
+           sb.append('\n');
+        }
+
+        LockInfo[] locks = inf.getLockedSynchronizers();
+        if (locks.length > 0) {
+           sb.append("\n\tNumber of locked synchronizers = ").append(locks.length);
+           sb.append('\n');
+           for (LockInfo li : locks) {
+               sb.append("\t- ").append(li);
+               sb.append('\n');
+           }
+        }
+        sb.append('\n');
+        return sb.toString();
+    }
+
+    static void pause(long millis) throws InterruptedException {
+        Thread.sleep(millis);
+    }
+
+    static void fail(Exception x) {
+        x.printStackTrace(System.err);
+        if (thrown == null) {
+            thrown = x;
+        }
+        goOn = false;
+    }
+
+    static void deadlock(Exception x) {
+        deadlock = true;
+        System.out.flush();
+        fail(x);
+        System.err.flush();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/util/logging/LogManager/Configuration/TestConfigurationLock.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,22 @@
+########################################################################
+#  Logging configuration property file for TestConfigurationLock.java  #
+########################################################################
+
+handlers= java.util.logging.ConsoleHandler
+
+.level= INFO
+
+java.util.logging.FileHandler.pattern = %h/java%u.log
+java.util.logging.FileHandler.limit = 50000
+java.util.logging.FileHandler.count = 1
+java.util.logging.FileHandler.formatter = java.util.logging.XMLFormatter
+
+java.util.logging.ConsoleHandler.level = INFO
+java.util.logging.ConsoleHandler.formatter = java.util.logging.SimpleFormatter
+
+blah.level = FINE
+foo.bar.l10.level = INFO
+foo.bar.l100.level = INFO
+foo.bar.l1000.level = INFO
+
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/javax/crypto/SecretKeyFactory/PBKDF2TranslateTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,270 @@
+/*
+ * 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.
+ */
+
+import java.security.InvalidKeyException;
+import java.security.NoSuchAlgorithmException;
+import java.security.spec.InvalidKeySpecException;
+import java.util.Arrays;
+import java.util.Random;
+import javax.crypto.SecretKey;
+import javax.crypto.SecretKeyFactory;
+import javax.crypto.interfaces.PBEKey;
+import javax.crypto.spec.PBEKeySpec;
+import javax.security.auth.DestroyFailedException;
+
+import static java.lang.System.out;
+
+/*
+ * @test
+ * @bug 8048820
+ * @summary The test verifies if the SecretKeyFactory.translateKey() method
+ *  works as expected for the PBKDF2 algorithms.
+ */
+
+public class PBKDF2TranslateTest {
+
+    private static final String PASS_PHRASE = "some hidden string";
+    private static final int ITERATION_COUNT = 1000;
+    private static final int KEY_SIZE = 128;
+    private static final String[] TEST_ALGOS = { "PBKDF2WithHmacSHA1",
+            "PBKDF2WithHmacSHA224", "PBKDF2WithHmacSHA256",
+            "PBKDF2WithHmacSHA384", "PBKDF2WithHmacSHA512" };
+    private final String algoForTest;
+
+    public static void main(String[] args) throws Exception {
+        for (String algo : TEST_ALGOS) {
+            PBKDF2TranslateTest theTest = new PBKDF2TranslateTest(algo);
+            byte[] salt = new byte[8];
+            new Random().nextBytes(salt);
+            theTest.testMyOwnSecretKey(salt);
+            theTest.generateAndTranslateKey(salt);
+            theTest.translateSpoiledKey(salt);
+        }
+    }
+
+    public PBKDF2TranslateTest(String algo) {
+        algoForTest = algo;
+    }
+
+    /**
+     * The test case scenario implemented in the method: - derive PBKDF2 key
+     * using the given algorithm; - translate the key - check if the translated
+     * and original keys have the same key value.
+     *
+     */
+    public void generateAndTranslateKey(byte[] salt)
+            throws NoSuchAlgorithmException, InvalidKeySpecException,
+            InvalidKeyException {
+        // derive PBKDF2 key
+        SecretKey key1 = getSecretKeyForPBKDF2(algoForTest, salt);
+
+        // translate key
+        SecretKeyFactory skf = SecretKeyFactory.getInstance(algoForTest);
+        SecretKey key2 = skf.translateKey(key1);
+
+        // Check if it still the same after translation
+        if (!Arrays.equals(key1.getEncoded(), key2.getEncoded())) {
+            System.out.println("Key1=" + new String(key1.getEncoded())
+                    + " key2=" + new String(key2.getEncoded()) + " salt="
+                    + new String(salt));
+            throw new RuntimeException(
+                    "generateAndTranslateKey test case failed: the  key1 and"
+                            + " key2 values in its primary encoding format are"
+                            + " not the same for " + algoForTest
+                            + " algorithm.");
+        }
+    }
+
+    /**
+     * The test case scenario implemented in the method: - derive Key1 for the
+     * given PBKDF2 algorithm - create my own secret Key2 as an instance of a
+     * class implements PBEKey - translate Key2 - check if the key value of the
+     * translated key and Key1 are the same.
+     */
+    private void testMyOwnSecretKey(byte[] salt)
+            throws NoSuchAlgorithmException, InvalidKeySpecException,
+            InvalidKeyException {
+        SecretKey key1 = getSecretKeyForPBKDF2(algoForTest, salt);
+        SecretKey key2 = getMyOwnSecretKey(salt);
+
+        // Is it actually the same?
+        if (!Arrays.equals(key1.getEncoded(), key2.getEncoded())) {
+            throw new RuntimeException(
+                    "We shouldn't be here. The key1 and key2 values in its"
+                            + " primary encoding format have to be the same!");
+        }
+
+        // translate key
+        SecretKeyFactory skf = SecretKeyFactory.getInstance(algoForTest);
+        SecretKey key3 = skf.translateKey(key2);
+
+        // Check if it still the same after translation
+        if (!Arrays.equals(key1.getEncoded(), key3.getEncoded())) {
+            System.out.println("Key1=" + new String(key1.getEncoded())
+                    + " key3=" + new String(key3.getEncoded()) + " salt="
+                    + new String(salt));
+            throw new RuntimeException(
+                    "testMyOwnSecretKey test case failed: the key1  and key3"
+                            + " values in its primary encoding format are not"
+                            + " the same for " + algoForTest + " algorithm.");
+        }
+
+    }
+
+    /**
+     * The test case scenario implemented in the method: - create my own secret
+     * Key2 as an instance of a class implements PBEKey - spoil the key (set
+     * iteration count to 0, for example) - try to translate key -
+     * InvalidKeyException is expected.
+     */
+    public void translateSpoiledKey(byte[] salt)
+            throws NoSuchAlgorithmException, InvalidKeySpecException {
+        // derive the key
+        SecretKey key1 = getMyOwnSecretKey(salt);
+
+        // spoil the key
+        ((MyPBKDF2SecretKey) key1).spoil();
+
+        // translate key
+        SecretKeyFactory skf = SecretKeyFactory.getInstance(algoForTest);
+        try {
+            skf.translateKey(key1);
+            throw new RuntimeException(
+                    "translateSpoiledKey test case failed, should throw"
+                            + " InvalidKeyException when spoil the key");
+        } catch (InvalidKeyException ike) {
+            out.println("Expected exception when spoil the key");
+        }
+
+    }
+
+    /**
+     * Generate a PBKDF2 secret key using given algorithm.
+     */
+    private SecretKey getSecretKeyForPBKDF2(String algoDeriveKey, byte[] salt)
+            throws NoSuchAlgorithmException, InvalidKeySpecException {
+
+        SecretKeyFactory skf = SecretKeyFactory.getInstance(algoDeriveKey);
+        PBEKeySpec spec = new PBEKeySpec(PASS_PHRASE.toCharArray(), salt,
+                ITERATION_COUNT, KEY_SIZE);
+
+        return skf.generateSecret(spec);
+    }
+
+    /**
+     * Generate a secrete key as an instance of a class implements PBEKey.
+     */
+    private SecretKey getMyOwnSecretKey(byte[] salt)
+            throws InvalidKeySpecException, NoSuchAlgorithmException {
+        return new MyPBKDF2SecretKey(PASS_PHRASE, algoForTest, salt,
+                ITERATION_COUNT, KEY_SIZE);
+    }
+
+    /**
+     * An utility class to check the SecretKeyFactory.translateKey() method.
+     */
+    class MyPBKDF2SecretKey implements PBEKey {
+        private final byte[] key;
+        private final byte[] salt;
+        private final String algorithm;
+        private final int keyLength;
+        private final String pass;
+        private int itereationCount;
+
+        /**
+         * The key is generating by SecretKeyFactory and its value just copying
+         * in the key field of MySecretKey class. So, this is real key derived
+         * using the given algo.
+         */
+        public MyPBKDF2SecretKey(String passPhrase, String algo, byte[] salt1,
+                int iterationCount, int keySize)
+                throws InvalidKeySpecException, NoSuchAlgorithmException {
+            algorithm = algo;
+            salt = salt1;
+            itereationCount = iterationCount;
+            pass = passPhrase;
+
+            PBEKeySpec spec = new PBEKeySpec(passPhrase.toCharArray(), salt,
+                    iterationCount, keySize);
+
+            SecretKeyFactory keyFactory = SecretKeyFactory.getInstance(algo);
+
+            SecretKey realKey = keyFactory.generateSecret(spec);
+
+            keyLength = realKey.getEncoded().length;
+
+            key = new byte[keyLength];
+            System.arraycopy(realKey.getEncoded(), 0, key, 0, keyLength);
+        }
+
+        @Override
+        public String getAlgorithm() {
+            return algorithm;
+        }
+
+        @Override
+        public String getFormat() {
+            return "RAW";
+        }
+
+        @Override
+        public byte[] getEncoded() {
+            byte[] copy = new byte[keyLength];
+            System.arraycopy(key, 0, copy, 0, keyLength);
+            return copy;
+        }
+
+        @Override
+        public int getIterationCount() {
+            return itereationCount;
+        }
+
+        @Override
+        public byte[] getSalt() {
+            return salt;
+        }
+
+        @Override
+        public char[] getPassword() {
+            return pass.toCharArray();
+        }
+
+        /**
+         * Spoil the generated key (before translation) to cause an
+         * InvalidKeyException
+         */
+        public void spoil() {
+            itereationCount = -1;
+        }
+
+        @Override
+        public void destroy() throws DestroyFailedException {
+        }
+
+        @Override
+        public boolean isDestroyed() {
+            return false;
+        }
+
+    }
+}
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/javax/crypto/SecretKeyFactory/SecKFTranslateTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,206 @@
+/*
+ * 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.
+ */
+
+import java.security.InvalidAlgorithmParameterException;
+import java.security.InvalidKeyException;
+import java.security.NoSuchAlgorithmException;
+import java.security.NoSuchProviderException;
+import java.security.SecureRandom;
+import java.security.spec.AlgorithmParameterSpec;
+import java.security.spec.InvalidKeySpecException;
+import java.util.Arrays;
+import java.util.Random;
+
+import javax.crypto.BadPaddingException;
+import javax.crypto.Cipher;
+import javax.crypto.IllegalBlockSizeException;
+import javax.crypto.NoSuchPaddingException;
+import javax.crypto.SecretKey;
+import javax.crypto.SecretKeyFactory;
+import javax.crypto.ShortBufferException;
+import javax.crypto.spec.PBEKeySpec;
+import javax.crypto.spec.PBEParameterSpec;
+import javax.security.auth.DestroyFailedException;
+
+/*
+ * @test
+ * @bug 8048820
+ * @summary The test verifies SecretKey values should remain the same after
+ *  translation with SecretKeyFactory.translateKey().
+ */
+
+public class SecKFTranslateTest {
+    private static final String SUN_JCE = "SunJCE";
+
+    public static void main(String[] args) throws Exception {
+
+        SecKFTranslateTest test = new SecKFTranslateTest();
+        test.run();
+    }
+
+    private void run() throws Exception {
+
+        for (Algorithm algorithm : Algorithm.values()) {
+            runTest(algorithm);
+        }
+    }
+
+    private void runTest(Algorithm algo) throws NoSuchAlgorithmException,
+            NoSuchProviderException, InvalidKeyException,
+            InvalidKeySpecException, NoSuchPaddingException,
+            InvalidAlgorithmParameterException, ShortBufferException,
+            IllegalBlockSizeException, BadPaddingException {
+        AlgorithmParameterSpec[] aps = new AlgorithmParameterSpec[1];
+        byte[] plainText = new byte[800];
+
+        SecretKey key1 = algo.intSecurityKey(aps);
+        Random random = new Random();
+        // Initialization
+        SecretKeyFactory skf = SecretKeyFactory.getInstance(algo.toString(),
+                SUN_JCE);
+
+        random.nextBytes(plainText);
+        Cipher ci = Cipher.getInstance(algo.toString(), SUN_JCE);
+        // Encryption
+        ci.init(Cipher.ENCRYPT_MODE, key1, aps[0]);
+        byte[] cipherText = new byte[ci.getOutputSize(plainText.length)];
+        int offset = ci.update(plainText, 0, plainText.length, cipherText, 0);
+        ci.doFinal(cipherText, offset);
+        // translate key
+        SecretKey key2 = skf.translateKey(key1);
+
+        // Decryption
+        ci.init(Cipher.DECRYPT_MODE, key2, aps[0]);
+        byte[] recoveredText = new byte[ci.getOutputSize(plainText.length)];
+        ci.doFinal(cipherText, 0, cipherText.length, recoveredText);
+
+        // Comparison
+        if (!Arrays.equals(plainText, recoveredText)) {
+            System.out.println("Key1:" + new String(key1.getEncoded())
+                    + " Key2:" + new String(key2.getEncoded()));
+            throw new RuntimeException("Testing translate key failed with "
+                    + algo);
+        }
+
+    }
+}
+
+class MyOwnSecKey implements SecretKey {
+
+    private static final String DEFAULT_ALGO = "PBEWithMD5AndDES";
+    private final byte[] key;
+    private final String algorithm;
+    private final int keySize;
+
+    public MyOwnSecKey(byte[] key1, int offset, String algo)
+            throws InvalidKeyException {
+        algorithm = algo;
+        if (algo.equalsIgnoreCase("DES")) {
+            keySize = 8;
+        } else if (algo.equalsIgnoreCase("DESede")) {
+            keySize = 24;
+        } else {
+            throw new InvalidKeyException(
+                    "Inappropriate key format and algorithm");
+        }
+
+        if (key1 == null || key1.length - offset < keySize) {
+            throw new InvalidKeyException("Wrong key size");
+        }
+        key = new byte[keySize];
+        System.arraycopy(key, offset, key, 0, keySize);
+    }
+
+    public MyOwnSecKey(PBEKeySpec ks) throws InvalidKeySpecException {
+        algorithm = DEFAULT_ALGO;
+        key = new String(ks.getPassword()).getBytes();
+        keySize = key.length;
+    }
+
+    @Override
+    public String getAlgorithm() {
+        return algorithm;
+    }
+
+    @Override
+    public String getFormat() {
+        return "RAW";
+    }
+
+    @Override
+    public byte[] getEncoded() {
+        byte[] copy = new byte[keySize];
+        System.arraycopy(key, 0, copy, 0, keySize);
+        return copy;
+    }
+
+    @Override
+    public void destroy() throws DestroyFailedException {
+    }
+
+    @Override
+    public boolean isDestroyed() {
+        return false;
+    }
+}
+
+enum Algorithm {
+    DES {
+        @Override
+        SecretKey intSecurityKey(AlgorithmParameterSpec[] spec)
+                throws InvalidKeyException {
+            int keyLength = 8;
+            byte[] keyVal = new byte[keyLength];
+            new SecureRandom().nextBytes(keyVal);
+            SecretKey key1 = new MyOwnSecKey(keyVal, 0, this.toString());
+            return key1;
+        }
+    },
+    DESEDE {
+        @Override
+        SecretKey intSecurityKey(AlgorithmParameterSpec[] spec)
+                throws InvalidKeyException {
+            int keyLength = 24;
+            byte[] keyVal = new byte[keyLength];
+            new SecureRandom().nextBytes(keyVal);
+            SecretKey key1 = new MyOwnSecKey(keyVal, 0, this.toString());
+            return key1;
+        }
+    },
+    PBEWithMD5ANDdes {
+        @Override
+        SecretKey intSecurityKey(AlgorithmParameterSpec[] spec)
+                throws InvalidKeySpecException {
+            byte[] salt = new byte[8];
+            int iterCnt = 6;
+            new Random().nextBytes(salt);
+            spec[0] = new PBEParameterSpec(salt, iterCnt);
+            PBEKeySpec pbeKS = new PBEKeySpec(
+                    new String("So far so good").toCharArray());
+            SecretKey key1 = new MyOwnSecKey(pbeKS);
+            return key1;
+        }
+    };
+    abstract SecretKey intSecurityKey(AlgorithmParameterSpec[] spec)
+            throws InvalidKeyException, InvalidKeySpecException;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/javax/script/SimpleScriptContextNameChecksTest.java	Wed Jul 05 20:35:10 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.
+ */
+
+/*
+ * @test
+ * @bug 8072853
+ * @summary SimpleScriptContext used by NashornScriptEngine doesn't completely complies to the spec regarding exception throwing
+ * @run testng SimpleScriptContextNameChecksTest
+ */
+
+import java.util.List;
+import java.util.function.Consumer;
+import javax.script.*;
+import org.testng.annotations.Test;
+
+public class SimpleScriptContextNameChecksTest {
+    private List<ScriptEngineFactory> getFactories() {
+        return new ScriptEngineManager().getEngineFactories();
+    }
+
+    private void testAndExpect(Consumer<ScriptContext> c, Class<? extends RuntimeException> clazz) {
+        for (ScriptEngineFactory fac : getFactories()) {
+            ScriptContext sc = fac.getScriptEngine().getContext();
+            String name = fac.getEngineName();
+            try {
+                c.accept(sc);
+                throw new RuntimeException("no exception for " + name);
+            } catch (NullPointerException | IllegalArgumentException e) {
+                if (e.getClass() == clazz) {
+                    System.out.println("got " + e + " as expected for " + name);
+                } else {
+                    throw e;
+                }
+            }
+        }
+    }
+
+    private void testAndExpectIAE(Consumer<ScriptContext> c) {
+        testAndExpect(c, IllegalArgumentException.class);
+    }
+
+    private void testAndExpectNPE(Consumer<ScriptContext> c) {
+        testAndExpect(c, NullPointerException.class);
+    }
+
+    @Test
+    public void getAttributeEmptyName() {
+        testAndExpectIAE(sc -> sc.getAttribute("", ScriptContext.GLOBAL_SCOPE));
+    }
+
+    @Test
+    public void getAttributeNullName() {
+        testAndExpectNPE(sc -> sc.getAttribute(null, ScriptContext.GLOBAL_SCOPE));
+    }
+
+    @Test
+    public void removeAttributeEmptyName() {
+        testAndExpectIAE(sc -> sc.removeAttribute("", ScriptContext.GLOBAL_SCOPE));
+    }
+
+    @Test
+    public void removeAttributeNullName() {
+        testAndExpectNPE(sc -> sc.removeAttribute(null, ScriptContext.GLOBAL_SCOPE));
+    }
+
+    @Test
+    public void setAttributeEmptyName() {
+        testAndExpectIAE(sc -> sc.setAttribute("", "value", ScriptContext.GLOBAL_SCOPE));
+    }
+
+    @Test
+    public void setAttributeNullName() {
+        testAndExpectNPE(sc -> sc.setAttribute(null, "value", ScriptContext.GLOBAL_SCOPE));
+    }
+
+    @Test
+    public void getAttributesScopeEmptyName() {
+        testAndExpectIAE(sc -> sc.getAttributesScope(""));
+    }
+
+    @Test
+    public void getAttributesScopeNullName() {
+        testAndExpectNPE(sc -> sc.getAttributesScope(null));
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/javax/xml/crypto/dsig/ErrorHandlerPermissions.java	Wed Jul 05 20:35:10 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.  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.ByteArrayInputStream;
+import java.io.File;
+import java.security.KeyFactory;
+import java.security.PublicKey;
+import java.security.spec.X509EncodedKeySpec;
+import java.util.Base64;
+import javax.xml.XMLConstants;
+import javax.xml.crypto.Data;
+import javax.xml.crypto.KeySelector;
+import javax.xml.crypto.OctetStreamData;
+import javax.xml.crypto.URIDereferencer;
+import javax.xml.crypto.URIReference;
+import javax.xml.crypto.URIReferenceException;
+import javax.xml.crypto.XMLCryptoContext;
+import javax.xml.crypto.dsig.XMLSignature;
+import javax.xml.crypto.dsig.XMLSignatureFactory;
+import javax.xml.crypto.dsig.dom.DOMValidateContext;
+import javax.xml.parsers.DocumentBuilderFactory;
+import org.w3c.dom.Document;
+import org.w3c.dom.Element;
+import org.w3c.dom.NodeList;
+
+/**
+ * @test
+ * @bug 8079140
+ * @summary Check if IgnoreAllErrorHandler doesn't require additional permission
+ * @run main/othervm/java.security.policy=ErrorHandlerPermissions.policy
+ *                                                      ErrorHandlerPermissions
+ */
+public class ErrorHandlerPermissions {
+
+    private final static String FS = System.getProperty("file.separator");
+    private final static String DIR = System.getProperty("test.src", ".");
+    private final static String DATA_DIR = DIR + FS + "data";
+    private final static String SIGNATURE = DATA_DIR + FS +
+            "signature-external-rsa.xml";
+
+    private static final String validationKey =
+        "MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCnx4TdvPSA5vcsPi0OJZi9Ox0Z" +
+        "2FRz2oeUCtuWoyEg0kUCeFd+jJZMstDJUiZNSOeuCO3FWSpdJgAwI4zlveHvuU/o" +
+        "qHSa1eYTObOCvxfVYGGflWsSvGXyiANtRWVUrYODBeyL+2pWxDYh+Fi5EKizPfTG" +
+        "wRjBVRSkRZKTnSjnQwIDAQAB";
+
+    private static final URIDereferencer dereferencer =
+            new DummyURIDereferencer();
+
+    public static void main(String[] args) throws Exception {
+        DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
+        dbf.setNamespaceAware(true);
+        dbf.setValidating(false);
+        dbf.setFeature(XMLConstants.FEATURE_SECURE_PROCESSING, Boolean.TRUE);
+        Document doc = dbf.newDocumentBuilder().parse(new File(SIGNATURE));
+        NodeList nl = doc.getElementsByTagNameNS(XMLSignature.XMLNS,
+                "Signature");
+        if (nl.getLength() == 0) {
+            throw new RuntimeException("Couldn't find 'Signature' element");
+        }
+        Element element = (Element) nl.item(0);
+
+        byte[] keyBytes = Base64.getDecoder().decode(validationKey);
+        X509EncodedKeySpec spec = new X509EncodedKeySpec(keyBytes);
+        KeyFactory kf = KeyFactory.getInstance("RSA");
+        PublicKey key = kf.generatePublic(spec);
+        KeySelector ks = KeySelector.singletonKeySelector(key);
+
+        DOMValidateContext vc = new DOMValidateContext(ks, element);
+
+        // disable secure validation mode
+        vc.setProperty("org.jcp.xml.dsig.secureValidation", Boolean.FALSE);
+
+        // set a dummy dereferencer to be able to get content by references
+        vc.setURIDereferencer(dereferencer);
+
+        XMLSignatureFactory factory = XMLSignatureFactory.getInstance();
+        XMLSignature signature = factory.unmarshalXMLSignature(vc);
+
+        // run validation
+        signature.validate(vc);
+    }
+
+    /**
+     * This URIDereferencer returns a static XML document.
+     */
+    private static class DummyURIDereferencer implements URIDereferencer {
+
+        @Override
+        public Data dereference(final URIReference ref, XMLCryptoContext ctx)
+                throws URIReferenceException {
+            // return static content
+            return new OctetStreamData(new ByteArrayInputStream(
+                    "<test>test</test>".getBytes()), ref.getURI(),
+                    ref.getType());
+        }
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/javax/xml/crypto/dsig/ErrorHandlerPermissions.policy	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,5 @@
+grant {
+    permission java.util.PropertyPermission "test.src", "read";
+    permission java.util.PropertyPermission "file.separator", "read";
+    permission java.io.FilePermission "${test.src}/-", "read";
+};
--- a/jdk/test/javax/xml/crypto/dsig/GenerationTests.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/javax/xml/crypto/dsig/GenerationTests.java	Wed Jul 05 20:35:10 2017 +0200
@@ -24,7 +24,7 @@
 /**
  * @test
  * @bug 4635230 6283345 6303830 6824440 6867348 7094155 8038184 8038349 8046949
- *      8046724
+ *      8046724 8079693
  * @summary Basic unit tests for generating XML Signatures with JSR 105
  * @compile -XDignore.symbol.file KeySelectors.java SignatureValidator.java
  *     X509KeySelector.java GenerationTests.java
@@ -92,7 +92,8 @@
                                    rsaSha256, rsaSha384, rsaSha512,
                                    ecdsaSha1;
     private static DigestMethod sha1, sha256, sha384, sha512;
-    private static KeyInfo dsa1024, dsa2048, rsa, rsa1024, p256ki;
+    private static KeyInfo dsa1024, dsa2048, rsa, rsa1024,
+                           p256ki, p384ki, p521ki;
     private static KeySelector kvks = new KeySelectors.KeyValueKeySelector();
     private static KeySelector sks;
     private static Key signingKey;
@@ -131,6 +132,8 @@
         test_create_signature_enveloping_hmac_sha512();
         test_create_signature_enveloping_rsa();
         test_create_signature_enveloping_p256_sha1();
+        test_create_signature_enveloping_p384_sha1();
+        test_create_signature_enveloping_p521_sha1();
         test_create_signature_external_b64_dsa();
         test_create_signature_external_dsa();
         test_create_signature_keyname();
@@ -186,7 +189,11 @@
         rsa1024 = kifac.newKeyInfo(Collections.singletonList
             (kifac.newKeyValue(getPublicKey("RSA", 1024))));
         p256ki = kifac.newKeyInfo(Collections.singletonList
-            (kifac.newKeyValue(getECPublicKey())));
+            (kifac.newKeyValue(getECPublicKey("P256"))));
+        p384ki = kifac.newKeyInfo(Collections.singletonList
+            (kifac.newKeyValue(getECPublicKey("P384"))));
+        p521ki = kifac.newKeyInfo(Collections.singletonList
+            (kifac.newKeyValue(getECPublicKey("P521"))));
         rsaSha1 = fac.newSignatureMethod(SignatureMethod.RSA_SHA1, null);
         rsaSha256 = fac.newSignatureMethod
             ("http://www.w3.org/2001/04/xmldsig-more#rsa-sha256", null);
@@ -359,7 +366,21 @@
     static void test_create_signature_enveloping_p256_sha1() throws Exception {
         System.out.println("* Generating signature-enveloping-p256-sha1.xml");
         test_create_signature_enveloping(sha1, ecdsaSha1, p256ki,
-            getECPrivateKey(), kvks, false);
+            getECPrivateKey("P256"), kvks, false);
+        System.out.println();
+    }
+
+    static void test_create_signature_enveloping_p384_sha1() throws Exception {
+        System.out.println("* Generating signature-enveloping-p384-sha1.xml");
+        test_create_signature_enveloping(sha1, ecdsaSha1, p384ki,
+            getECPrivateKey("P384"), kvks, false);
+        System.out.println();
+    }
+
+    static void test_create_signature_enveloping_p521_sha1() throws Exception {
+        System.out.println("* Generating signature-enveloping-p521-sha1.xml");
+        test_create_signature_enveloping(sha1, ecdsaSha1, p521ki,
+            getECPrivateKey("P521"), kvks, false);
         System.out.println();
     }
 
@@ -1189,37 +1210,63 @@
         "237008997971129772408397621801631622129297063463868593083106979716" +
         "204903524890556839550490384015324575598723478554854070823335021842" +
         "210112348400928769";
-    private static final String EC_X =
+    private static final String EC_P256_X =
         "335863644451761614592446380116804721648611739647823420286081723541" +
         "6166183710";
-    private static final String EC_Y =
+    private static final String EC_P256_Y =
         "951559601159729477487064127150143688502130342917782252098602422796" +
         "95457910701";
-    private static final String EC_S =
+    private static final String EC_P256_S =
         "425976209773168452211813225517384419928639977904006759709292218082" +
         "7440083936";
-    private static final ECParameterSpec EC_PARAMS;
+    private static final ECParameterSpec EC_P256_PARAMS = initECParams(
+        "FFFFFFFF00000001000000000000000000000000FFFFFFFFFFFFFFFFFFFFFFFF",
+        "FFFFFFFF00000001000000000000000000000000FFFFFFFFFFFFFFFFFFFFFFFC",
+        "5AC635D8AA3A93E7B3EBBD55769886BC651D06B0CC53B0F63BCE3C3E27D2604B",
+        "6B17D1F2E12C4247F8BCE6E563A440F277037D812DEB33A0F4A13945D898C296",
+        "4FE342E2FE1A7F9B8EE7EB4A7C0F9E162BCE33576B315ECECBB6406837BF51F5",
+        "FFFFFFFF00000000FFFFFFFFFFFFFFFFBCE6FAADA7179E84F3B9CAC2FC632551",
+        1
+    );
+    private static final String EC_P384_X =
+        "12144058647679082341340699736608428955270957565259459672517275506071643671835484144490620216582303669654008841724053";
+    private static final String EC_P384_Y =
+        "18287745972107701566600963632634101287058332546756092926848497481238534346489545826483592906634896557151987868614320";
+    private static final String EC_P384_S =
+        "10307785759830534742680442271492590599236624208247590184679565032330507874096079979152605984203102224450595283943382";
+    private static final ECParameterSpec EC_P384_PARAMS = initECParams(
+        "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFFFF0000000000000000FFFFFFFF",
+        "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFFFF0000000000000000FFFFFFFC",
+        "B3312FA7E23EE7E4988E056BE3F82D19181D9C6EFE8141120314088F5013875AC656398D8A2ED19D2A85C8EDD3EC2AEF",
+        "AA87CA22BE8B05378EB1C71EF320AD746E1D3B628BA79B9859F741E082542A385502F25DBF55296C3A545E3872760AB7",
+        "3617DE4A96262C6F5D9E98BF9292DC29F8F41DBD289A147CE9DA3113B5F0B8C00A60B1CE1D7E819D7A431D7C90EA0E5F",
+        "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFC7634D81F4372DDF581A0DB248B0A77AECEC196ACCC52973",
+        1
+    );
+    private static final String EC_P521_X =
+        "4157918188927862838251799402582135611021257663417126086145819679867926857146776190737187582274664373117054717389603317411991660346043842712448912355335343997";
+    private static final String EC_P521_Y =
+        "4102838062751704796157456866854813794620023146924181568434486703918224542844053923233919899911519054998554969832861957437850996213216829205401947264294066288";
+    private static final String EC_P521_S =
+        "4857798533181496041050215963883119936300918353498701880968530610687256097257307590162398707429640390843595868713096292822034014722985178583665959048714417342";
+    private static final ECParameterSpec EC_P521_PARAMS = initECParams(
+        "01FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF",
+        "01FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFC",
+        "0051953EB9618E1C9A1F929A21A0B68540EEA2DA725B99B315F3B8B489918EF109E156193951EC7E937B1652C0BD3BB1BF073573DF883D2C34F1EF451FD46B503F00",
+        "00C6858E06B70404E9CD9E3ECB662395B4429C648139053FB521F828AF606B4D3DBAA14B5E77EFE75928FE1DC127A2FFA8DE3348B3C1856A429BF97E7E31C2E5BD66",
+        "011839296A789A3BC0045C8A5FB42C7D1BD998F54449579B446817AFBD17273E662C97EE72995EF42640C550B9013FAD0761353C7086A272C24088BE94769FD16650",
+        "01FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFA51868783BF2F966B7FCC0148F709A5D03BB5C9B8899C47AEBB6FB71E91386409",
+        1
+    );
 
-    static {
-        final String ec_sfield, ec_a, ec_b, ec_gx, ec_gy, ec_n;
-        ec_sfield =
-            "FFFFFFFF00000001000000000000000000000000FFFFFFFFFFFFFFFFFFFFFFFF";
-        ec_a =
-            "FFFFFFFF00000001000000000000000000000000FFFFFFFFFFFFFFFFFFFFFFFC";
-        ec_b =
-            "5AC635D8AA3A93E7B3EBBD55769886BC651D06B0CC53B0F63BCE3C3E27D2604B";
-        ec_gx =
-            "6B17D1F2E12C4247F8BCE6E563A440F277037D812DEB33A0F4A13945D898C296";
-        ec_gy =
-            "4FE342E2FE1A7F9B8EE7EB4A7C0F9E162BCE33576B315ECECBB6406837BF51F5";
-        ec_n =
-            "FFFFFFFF00000000FFFFFFFFFFFFFFFFBCE6FAADA7179E84F3B9CAC2FC632551";
-        final int ec_h = 1;
-        final ECField ec_field = new ECFieldFp(bigInt(ec_sfield));
-        final EllipticCurve ec_curve = new EllipticCurve(ec_field,
-                                                bigInt(ec_a), bigInt(ec_b));
-        final ECPoint ec_g = new ECPoint(bigInt(ec_gx), bigInt(ec_gy));
-        EC_PARAMS = new ECParameterSpec(ec_curve, ec_g, bigInt(ec_n), ec_h);
+    private static ECParameterSpec initECParams(
+            String sfield, String a, String b, String gx, String gy,
+            String n, int h) {
+        ECField field = new ECFieldFp(bigInt(sfield));
+        EllipticCurve curve = new EllipticCurve(field,
+                                                bigInt(a), bigInt(b));
+        ECPoint g = new ECPoint(bigInt(gx), bigInt(gy));
+        return new ECParameterSpec(curve, g, bigInt(n), h);
     }
 
     private static BigInteger bigInt(String s) {
@@ -1253,11 +1300,32 @@
         return kf.generatePublic(kspec);
     }
 
-    private static PublicKey getECPublicKey() throws Exception {
+    private static PublicKey getECPublicKey(String curve) throws Exception {
         KeyFactory kf = KeyFactory.getInstance("EC");
-        KeySpec kspec = new ECPublicKeySpec(new ECPoint(new BigInteger(EC_X),
-                                                        new BigInteger(EC_Y)),
-                                            EC_PARAMS);
+        String x, y;
+        ECParameterSpec params;
+        switch (curve) {
+            case "P256":
+                x = EC_P256_X;
+                y = EC_P256_Y;
+                params = EC_P256_PARAMS;
+                break;
+            case "P384":
+                x = EC_P384_X;
+                y = EC_P384_Y;
+                params = EC_P384_PARAMS;
+                break;
+            case "P521":
+                x = EC_P521_X;
+                y = EC_P521_Y;
+                params = EC_P521_PARAMS;
+                break;
+            default:
+                throw new Exception("Unsupported curve: " + curve);
+        }
+        KeySpec kspec = new ECPublicKeySpec(new ECPoint(new BigInteger(x),
+                                                        new BigInteger(y)),
+                                            params);
         return kf.generatePublic(kspec);
     }
 
@@ -1287,9 +1355,27 @@
         return kf.generatePrivate(kspec);
     }
 
-    private static PrivateKey getECPrivateKey() throws Exception {
+    private static PrivateKey getECPrivateKey(String curve) throws Exception {
+        String s;
+        ECParameterSpec params;
+        switch (curve) {
+            case "P256":
+                s = EC_P256_S;
+                params = EC_P256_PARAMS;
+                break;
+            case "P384":
+                s = EC_P384_S;
+                params = EC_P384_PARAMS;
+                break;
+            case "P521":
+                s = EC_P521_S;
+                params = EC_P521_PARAMS;
+                break;
+            default:
+                throw new Exception("Unsupported curve: " + curve);
+        }
         KeyFactory kf = KeyFactory.getInstance("EC");
-        KeySpec kspec = new ECPrivateKeySpec(new BigInteger(EC_S), EC_PARAMS);
+        KeySpec kspec = new ECPrivateKeySpec(new BigInteger(s), params);
         return kf.generatePrivate(kspec);
     }
 
--- a/jdk/test/javax/xml/crypto/dsig/ValidationTests.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/javax/xml/crypto/dsig/ValidationTests.java	Wed Jul 05 20:35:10 2017 +0200
@@ -23,7 +23,7 @@
 
 /**
  * @test
- * @bug 4635230 6365103 6366054 6824440 7131084 8046724
+ * @bug 4635230 6365103 6366054 6824440 7131084 8046724 8079693
  * @summary Basic unit tests for validating XML Signatures with JSR 105
  * @compile -XDignore.symbol.file KeySelectors.java SignatureValidator.java
  *     X509KeySelector.java ValidationTests.java
@@ -35,6 +35,7 @@
 import java.security.*;
 import javax.xml.crypto.Data;
 import javax.xml.crypto.KeySelector;
+import javax.xml.crypto.MarshalException;
 import javax.xml.crypto.OctetStreamData;
 import javax.xml.crypto.URIDereferencer;
 import javax.xml.crypto.URIReference;
@@ -60,9 +61,17 @@
     static class Test {
         String file;
         KeySelector ks;
-        Test(String file, KeySelector ks) {
+        Class exception;
+
+        Test(String file, KeySelector ks, Class exception) {
             this.file = file;
             this.ks = ks;
+            this.exception = exception;
+        }
+
+        // XMLSignatureException is expected by default
+        Test(String file, KeySelector ks) {
+            this(file, ks, XMLSignatureException.class);
         }
     }
 
@@ -91,6 +100,8 @@
         new Test("signature-enveloping-dsa.xml", KVKS),
         new Test("signature-enveloping-rsa.xml", KVKS),
         new Test("signature-enveloping-p256-sha1.xml", KVKS),
+        new Test("signature-enveloping-p384-sha1.xml", KVKS),
+        new Test("signature-enveloping-p521-sha1.xml", KVKS),
         new Test("signature-enveloping-hmac-sha1.xml", SKKS),
         new Test("signature-external-dsa.xml", KVKS),
         new Test("signature-external-b64-dsa.xml", KVKS),
@@ -110,7 +121,17 @@
     private final static Test[] INVALID_TESTS = {
         new Test("signature-enveloping-hmac-sha1-40.xml", SKKS),
         new Test("signature-enveloping-hmac-sha1-trunclen-0-attack.xml", SKKS),
-        new Test("signature-enveloping-hmac-sha1-trunclen-8-attack.xml", SKKS)
+        new Test("signature-enveloping-hmac-sha1-trunclen-8-attack.xml", SKKS),
+        new Test("signature-extra-text-in-signed-info.xml", SKKS,
+                MarshalException.class),
+        new Test("signature-wrong-canonicalization-method-algorithm.xml", SKKS,
+                MarshalException.class),
+        new Test("signature-wrong-transform-algorithm.xml", SKKS,
+                MarshalException.class),
+        new Test("signature-no-reference-uri.xml", SKKS),
+        new Test("signature-wrong-signature-method-algorithm.xml", SKKS,
+                MarshalException.class),
+        new Test("signature-wrong-tag-names.xml", SKKS, MarshalException.class)
     };
 
     public static void main(String args[]) throws Exception {
@@ -143,9 +164,14 @@
                 test_signature(test);
                 System.out.println("FAILED");
                 atLeastOneFailed = true;
-            } catch (XMLSignatureException xse) {
-                System.out.println(xse.getMessage());
-                System.out.println("PASSED");
+            } catch (Exception e) {
+                System.out.println("Exception: " + e);
+                if (e.getClass() != test.exception) {
+                    System.out.println("FAILED: unexpected exception");
+                    atLeastOneFailed = true;
+                } else {
+                    System.out.println("PASSED");
+                }
             }
         }
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/javax/xml/crypto/dsig/data/signature-enveloping-p384-sha1.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,3 @@
+<?xml version="1.0" encoding="UTF-8" standalone="no"?><Signature xmlns="http://www.w3.org/2000/09/xmldsig#"><SignedInfo><CanonicalizationMethod Algorithm="http://www.w3.org/TR/2001/REC-xml-c14n-20010315"/><SignatureMethod Algorithm="http://www.w3.org/2001/04/xmldsig-more#ecdsa-sha1"/><Reference URI="#object"><DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1"/><DigestValue>7/XTsHaBSOnJ/jXD5v0zL6VKYsk=</DigestValue></Reference></SignedInfo><SignatureValue>s15F4ng4a+TfNHlK+y18igexSe3wRspeyQi8hwhyMUh6I6kyzxO1wcqRulFyBNwh/Dplht+WS9dO
+GwL4xfDfozKss36ZsHACI3EYe0QI6pN7hcKp511muPI+cmoZzIN/</SignatureValue><KeyInfo><KeyValue><ECKeyValue xmlns="http://www.w3.org/2009/xmldsig11#"><NamedCurve URI="urn:oid:1.3.132.0.34"/><PublicKey>BE7my2bSrGpZ3jNFQ1I6baGP9CE4AIMIyN/ugWhbsCQz8ntwXf15NStBt9MBXolglXbRYMqV8vYB
+f7UJ1ixum8hzcEvgShn0L9l1VkWaU4bYr/Ss9ApimDvbF2g6Mw++sA==</PublicKey></ECKeyValue></KeyValue></KeyInfo><Object Id="object">some text</Object></Signature>
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/javax/xml/crypto/dsig/data/signature-enveloping-p521-sha1.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,5 @@
+<?xml version="1.0" encoding="UTF-8" standalone="no"?><Signature xmlns="http://www.w3.org/2000/09/xmldsig#"><SignedInfo><CanonicalizationMethod Algorithm="http://www.w3.org/TR/2001/REC-xml-c14n-20010315"/><SignatureMethod Algorithm="http://www.w3.org/2001/04/xmldsig-more#ecdsa-sha1"/><Reference URI="#object"><DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1"/><DigestValue>7/XTsHaBSOnJ/jXD5v0zL6VKYsk=</DigestValue></Reference></SignedInfo><SignatureValue>AaVkRumHXD0vVtkn2ogcAoByVge1KWGVWE6vph+xr/hcZTqNNaiIyXb7Itu0FBHD9M47T/CuM7y4
+m60zEssaaHl0AUNm7xGpZy7Heqaoibb/gMU1ErrfSNs7yuPG/TCqs8YAd3RGnc6ZbloitWpycGCU
+LS4xxKms0KeRnbVpjk5OeVfK</SignatureValue><KeyInfo><KeyValue><ECKeyValue xmlns="http://www.w3.org/2009/xmldsig11#"><NamedCurve URI="urn:oid:1.3.132.0.35"/><PublicKey>BAE2HJjBQRbl0sdGa1+1cJwxtPJXcnrRdmRXs6TEQmU97US+CK0vsoDQtlnXxDx37mawN7Sh4Atp
+CUeYBbzvBmwPfQEyAO600W9xn4s5wSQvXod8v8brh5ISXhxYPFy3SCcGUxbQYqrVUnBrIXH8WEQX
+K0/T+FdF4CzlQswJY0UZGeQYcA==</PublicKey></ECKeyValue></KeyValue></KeyInfo><Object Id="object">some text</Object></Signature>
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/javax/xml/crypto/dsig/data/signature-external-rsa.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,3 @@
+<test xmlns="http://example.org/envelope">test<Signature xmlns="http://www.w3.org/2000/09/xmldsig#"><SignedInfo xmlns="http://www.w3.org/2000/09/xmldsig#"><CanonicalizationMethod Algorithm="http://www.w3.org/TR/2001/REC-xml-c14n-20010315"></CanonicalizationMethod><SignatureMethod Algorithm="http://www.w3.org/2000/09/xmldsig#rsa-sha1"></SignatureMethod><Reference URI="http://oracle.com"><Transforms><Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature"></Transform></Transforms><DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1"></DigestMethod><DigestValue>1Bq8FsjajUBYPD7stQeJSc66GlM=</DigestValue></Reference></SignedInfo><SignatureValue>f6trDCcPsLLkIV/V4DGFbRf8b9Jwal8xGBDshNzEXwPmym2ChN85rbKIg/cbunf04F89/SXLo2v9
+AYjLcUr3G/Vz5YUmqNhnBvJukXgsIG0ddWl3mFi9Tk+CLINlbgfsaFqU9pQwFjmDyAqIrvZYqW7p
+rTHLetv218mbUVBBAkc=</SignatureValue></Signature></test>
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/javax/xml/crypto/dsig/data/signature-extra-text-in-signed-info.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,3 @@
+<test xmlns="http://example.org/envelope">test<Signature xmlns="http://www.w3.org/2000/09/xmldsig#"><SignedInfo xmlns="http://www.w3.org/2000/09/xmldsig#"><CanonicalizationMethod Algorithm="http://www.w3.org/TR/2001/REC-xml-c14n-20010315"></CanonicalizationMethod><SignatureMethod Algorithm="http://www.w3.org/2000/09/xmldsig#rsa-sha1"></SignatureMethod><Reference URI=""><Transforms><Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature"></Transform></Transforms><DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1"></DigestMethod><DigestValue>1Bq8FsjajUBYPD7stQeJSc66GlM=</DigestValue><test>extra text</test></Reference></SignedInfo><SignatureValue>iTrgJERmYeD5hFwY8/MwJpkF+nd++AAOgf/Kxt9SwdE6BIYq2Vyxq4CQPhD+t2971BGTgvF6ejZd
++/Ko4Zs5Dqf4Lt65Vck0q43rM0PdP1e8gJov0IPYnZ1zeqFpah+N/OjmqTbshaZWRIjf3eqS6en5
+ZKjn+TkCQ1kOX/YUNDc=</SignatureValue></Signature></test>
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/javax/xml/crypto/dsig/data/signature-no-reference-uri.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,3 @@
+<test xmlns="http://example.org/envelope">test<Signature xmlns="http://www.w3.org/2000/09/xmldsig#"><SignedInfo xmlns="http://www.w3.org/2000/09/xmldsig#"><CanonicalizationMethod Algorithm="http://www.w3.org/TR/2001/REC-xml-c14n-20010315"></CanonicalizationMethod><SignatureMethod Algorithm="http://www.w3.org/2000/09/xmldsig#rsa-sha1"></SignatureMethod><Reference><Transforms><Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature"></Transform></Transforms><DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1"></DigestMethod><DigestValue>1Bq8FsjajUBYPD7stQeJSc66GlM=</DigestValue></Reference></SignedInfo><SignatureValue>BNPSYlNcyXcO/Tc1tr9mQ/KAZ40eFybLTDyB/HH1EHHMpc972A+nOX2EWBaLsVgG8apl0Isp1ZqV
+gmoDHNF6xrcJJQVydVJzU08GVV4GiXHMqRYQbted7STQLhlhssvNNdMEoVApsX5ByL66wxKZQXrT
+z1kZtOHAi88DOrmIJu0=</SignatureValue></Signature></test>
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/javax/xml/crypto/dsig/data/signature-wrong-canonicalization-method-algorithm.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,3 @@
+<test xmlns="http://example.org/envelope">test<Signature xmlns="http://www.w3.org/2000/09/xmldsig#"><SignedInfo xmlns="http://www.w3.org/2000/09/xmldsig#"><CanonicalizationMethod Algorithm="http://oracle.com"></CanonicalizationMethod><SignatureMethod Algorithm="http://www.w3.org/2000/09/xmldsig#rsa-sha1"></SignatureMethod><Reference URI=""><Transforms><Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature"></Transform></Transforms><DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1"></DigestMethod><DigestValue>1Bq8FsjajUBYPD7stQeJSc66GlM=</DigestValue></Reference></SignedInfo><SignatureValue>EBbyEV7e+1CTUsyCTyxiN8p+U3/za1oTjK7q+kF8Q87r8e/7C1z4ndGWbk6zyI3w6leT+I2suW9U
+KkdvkrDXX2OyLw0GfgJfLkNn+1pGK6kyWpL95NoWJZhHkUAKKBZ0ikfZ4j33gYxrYK+IYCLeZYzr
+hlZjdXXXCiSH0Sq+weQ=</SignatureValue></Signature></test>
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/javax/xml/crypto/dsig/data/signature-wrong-signature-method-algorithm.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,3 @@
+<test xmlns="http://example.org/envelope">test<Signature xmlns="http://www.w3.org/2000/09/xmldsig#"><SignedInfo xmlns="http://www.w3.org/2000/09/xmldsig#"><CanonicalizationMethod Algorithm="http://www.w3.org/TR/2001/REC-xml-c14n-20010315"></CanonicalizationMethod><SignatureMethod Algorithm="bogus://bogus"></SignatureMethod><Reference URI=""><Transforms><Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature"></Transform></Transforms><DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1"></DigestMethod><DigestValue>1Bq8FsjajUBYPD7stQeJSc66GlM=</DigestValue></Reference></SignedInfo><SignatureValue>RjL9nfQg9u6+KEFfAlBBH7E7ilFgB7YEQ5MxOIJN/fOdQmc5iDD+YuhiHzNGXGi/UOyo6t8LxTxl
+X4oFE1RNlPVkSAZK4LcTWhVa757WwgW1/EZo8PQYWp5NScLq6PumYaujoovSYBKW2N6+jQpnD/L6
+4cuEVNnwEFqvOLrjogY=</SignatureValue></Signature></test>
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/javax/xml/crypto/dsig/data/signature-wrong-tag-names.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,3 @@
+<test xmlns="http://example.org/envelope">test<Signature xmlns="http://www.w3.org/2000/09/xmldsig#"><aSignedInfo xmlns="http://www.w3.org/2000/09/xmldsig#"><aCanonicalizationMethod Algorithm="http://www.w3.org/TR/2001/REC-xml-c14n-20010315"></aCanonicalizationMethod><aSignatureMethod Algorithm="http://www.w3.org/2000/09/xmldsig#rsa-sha1"></aSignatureMethod><aReference URI=""><Transforms><aTransform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature"></aTransform></Transforms><aDigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1"></aDigestMethod><aDigestValue>1Bq8FsjajUBYPD7stQeJSc66GlM=</aDigestValue></aReference></aSignedInfo><aSignatureValue>cbNpPGavhM0BGUtrvLxvy2SCIt+I27BPpVEt0Q9mXrdPYurMqWF/67AdY9m5RqS7+ZZlwUtem083
+MczRYbKoOIq7sMbCqKKdzbSE/U6rfmky/ACQ5wgemZl8jtipwu5LhAUzjhzT8hhTjVqOYpHdkVJz
+l9dnd9eWbLmEr3BI0VA=</aSignatureValue></Signature></test>
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/javax/xml/crypto/dsig/data/signature-wrong-transform-algorithm.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,4 @@
+<!-- This XML signature contains a Transform with wrong algorithm -->
+<test xmlns="http://example.org/envelope">test<Signature xmlns="http://www.w3.org/2000/09/xmldsig#"><SignedInfo xmlns="http://www.w3.org/2000/09/xmldsig#"><CanonicalizationMethod Algorithm="http://www.w3.org/TR/2001/REC-xml-c14n-20010315"></CanonicalizationMethod><SignatureMethod Algorithm="http://www.w3.org/2000/09/xmldsig#rsa-sha1"></SignatureMethod><Reference URI=""><Transforms><Transform Algorithm="bogus://bogus"></Transform></Transforms><DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1"></DigestMethod><DigestValue>1Bq8FsjajUBYPD7stQeJSc66GlM=</DigestValue></Reference></SignedInfo><SignatureValue>Wzyx3jgEKGwY+pBXBmqWLWhASHQYCCGZVii5sKKKeZUBKxNBthjiSVfzKANuLgX6zAt16XRycrSL
+zFKTPuvGeWVPDvd+KTNKCJxN9ccrG7v23EM7RY2eMJGu2r5DLfKwV7H6YuJPsOuWifVkKAhvq7gd
+6akJshxyAj9Ud+mjo48=</SignatureValue></Signature></test>
\ No newline at end of file
--- a/jdk/test/sun/management/jmxremote/bootstrap/CustomLauncherTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/sun/management/jmxremote/bootstrap/CustomLauncherTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -111,6 +111,8 @@
         try {
             String[] launcher = getLauncher();
 
+            if (launcher == null) return; // launcher not available for the tested platform; skip
+
             System.out.println("Starting custom launcher:");
             System.out.println("=========================");
             System.out.println("  launcher  : " + launcher[0]);
--- a/jdk/test/sun/nio/cs/FindDecoderBugs.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/sun/nio/cs/FindDecoderBugs.java	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 2010, 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
@@ -24,16 +24,19 @@
 /*
  * @test
  * @bug 6380723
- * @summary Decode many byte sequences in many ways
+ * @summary Decode many byte sequences in many ways (use -Dseed=X to set PRNG seed)
+ * @library /lib/testlibrary
+ * @build jdk.testlibrary.*
  * @run main/timeout=1800 FindDecoderBugs
  * @author Martin Buchholz
- * @key randomness
+ * @key intermittent randomness
  */
 
 import java.util.*;
 import java.util.regex.*;
 import java.nio.*;
 import java.nio.charset.*;
+import jdk.testlibrary.RandomFactory;
 
 public class FindDecoderBugs {
 
@@ -322,7 +325,7 @@
         }
     }
 
-    private final static Random rnd = new Random();
+    private final static Random rnd = RandomFactory.getRandom();
     private static byte randomByte() {
         return (byte) rnd.nextInt(0x100);
     }
--- a/jdk/test/sun/nio/cs/FindEncoderBugs.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/sun/nio/cs/FindEncoderBugs.java	Wed Jul 05 20:35:10 2017 +0200
@@ -25,15 +25,18 @@
  * @test
  * @bug 6233345 6381699 6381702 6381705 6381706
  * @summary Encode many char sequences in many ways
+ * @library /lib/testlibrary/
+ * @build jdk.testlibrary.*
  * @run main/timeout=1200 FindEncoderBugs
  * @author Martin Buchholz
- * @key randomness
+ * @key randomness intermittent
  */
 
 import java.util.*;
 import java.util.regex.*;
 import java.nio.*;
 import java.nio.charset.*;
+import jdk.testlibrary.RandomFactory;
 
 public class FindEncoderBugs {
 
@@ -456,7 +459,7 @@
         }
     }
 
-    private final static Random rnd = new Random();
+    private final static Random rnd = RandomFactory.getRandom();
     private static char randomChar() {
         return (char) rnd.nextInt(Character.MAX_VALUE);
     }
--- a/jdk/test/sun/nio/cs/TestStringCoding.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/sun/nio/cs/TestStringCoding.java	Wed Jul 05 20:35:10 2017 +0200
@@ -22,7 +22,7 @@
  */
 
 /* @test
-   @bug 6636323 6636319 7040220 7096080 7183053
+   @bug 6636323 6636319 7040220 7096080 7183053 8080248
    @summary Test if StringCoding and NIO result have the same de/encoding result
  * @run main/othervm/timeout=2000 TestStringCoding
  * @key randomness
@@ -200,6 +200,17 @@
             */
         }
 
+        //encode mappable surrogates for hkscs
+        if (cs.name().equals("Big5-HKSCS") || cs.name().equals("x-MS950-HKSCS")) {
+            String str = "ab\uD840\uDD0Ccd";
+            byte[] expected = new byte[] {(byte)'a', (byte)'b',
+                (byte)0x88, (byte)0x45, (byte)'c', (byte)'d' };
+            if (!Arrays.equals(str.getBytes(cs.name()), expected) ||
+                !Arrays.equals(str.getBytes(cs), expected)) {
+                throw new RuntimeException("encode(surrogates) failed  -> "
+                                           + cs.name());
+            }
+        }
     }
 
     static class PermissiveSecurityManger extends SecurityManager {
--- a/jdk/test/sun/security/krb5/auto/HttpNegotiateServer.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/sun/security/krb5/auto/HttpNegotiateServer.java	Wed Jul 05 20:35:10 2017 +0200
@@ -40,21 +40,34 @@
 import java.io.File;
 import java.io.FileOutputStream;
 import java.io.IOException;
+import java.io.InputStream;
 import java.io.InputStreamReader;
 import java.net.HttpURLConnection;
 import java.net.InetSocketAddress;
 import java.net.PasswordAuthentication;
 import java.net.Proxy;
 import java.net.URL;
-import java.security.PrivilegedExceptionAction;
+import java.net.URLConnection;
+import java.security.*;
 import java.util.HashMap;
 import java.util.Map;
 import javax.security.auth.Subject;
+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.auth.login.AppConfigurationEntry;
+import javax.security.auth.login.Configuration;
+import javax.security.auth.login.LoginContext;
+import javax.security.auth.login.LoginException;
+import javax.security.auth.login.AppConfigurationEntry.LoginModuleControlFlag;
 import org.ietf.jgss.GSSContext;
 import org.ietf.jgss.GSSCredential;
 import org.ietf.jgss.GSSManager;
 import sun.security.jgss.GSSUtil;
 import sun.security.krb5.Config;
+import java.util.Base64;
 import sun.util.logging.PlatformLogger;
 
 import java.util.Base64;
@@ -197,7 +210,7 @@
         proxyUrl = new URL("http://nosuchplace/a/b/c");
 
         try {
-            Exception e1 = null, e2 = null;
+            Exception e1 = null, e2 = null, e3 = null;
             try {
                 test6578647();
             } catch (Exception e) {
@@ -210,7 +223,14 @@
                 e2 = e;
                 e.printStackTrace();
             }
-            if (e1 != null || e2 != null) {
+            try {
+                test8077155();
+            } catch (Exception e) {
+                e3 = e;
+                e.printStackTrace();
+            }
+
+            if (e1 != null || e2 != null || e3 != null) {
                 throw new RuntimeException("Test error");
             }
         } finally {
@@ -254,6 +274,121 @@
         }
     }
 
+    static void testConnect() {
+        InputStream inputStream = null;
+        try {
+            URL url = webUrl;
+
+            URLConnection conn = url.openConnection();
+            conn.connect();
+            inputStream = conn.getInputStream();
+            byte[] b = new byte[inputStream.available()];
+            for (int j = 0; j < b.length; j++) {
+                b[j] = (byte) inputStream.read();
+            }
+            String s = new String(b);
+            System.out.println("Length: " + s.length());
+            System.out.println(s);
+        } catch (Exception ex) {
+              throw new RuntimeException(ex);
+        } finally {
+            if (inputStream != null) {
+                try {
+                    inputStream.close();
+                } catch (IOException e) {
+                    e.printStackTrace();
+                }
+            }
+        }
+    }
+
+    static void test8077155() throws Exception {
+        final String username = WEB_USER;
+        final char[] password = WEB_PASS;
+
+        SecurityManager security = new SecurityManager();
+        Policy.setPolicy(new SecurityPolicy());
+        System.setSecurityManager(security);
+
+        CallbackHandler callback = new CallbackHandler() {
+            @Override
+            public void handle(Callback[] pCallbacks) throws IOException, UnsupportedCallbackException {
+                for (Callback cb : pCallbacks) {
+                    if (cb instanceof NameCallback) {
+                        NameCallback ncb = (NameCallback)cb;
+                        ncb.setName(username);
+
+                    } else  if (cb instanceof PasswordCallback) {
+                        PasswordCallback pwdcb = (PasswordCallback) cb;
+                        pwdcb.setPassword(password);
+                    }
+                }
+            }
+
+        };
+
+        final String jaasConfigName = "oracle.test.kerberos.login";
+        final String krb5LoginModule = "com.sun.security.auth.module.Krb5LoginModule";
+
+        Configuration loginConfig = new Configuration() {
+            @Override
+            public AppConfigurationEntry[] getAppConfigurationEntry(String name) {
+                if (! jaasConfigName.equals(name)) {
+                    return new AppConfigurationEntry[0];
+                }
+
+                Map<String, String> options = new HashMap<String, String>();
+                options.put("useTicketCache", Boolean.FALSE.toString());
+                options.put("useKeyTab", Boolean.FALSE.toString());
+
+                return new AppConfigurationEntry[] {
+                        new AppConfigurationEntry(krb5LoginModule,
+                                LoginModuleControlFlag.REQUIRED,
+                                options)
+                        };
+            }
+        };
+
+        // oracle context/subject/login
+        LoginContext context = null;
+        try {
+            context = new LoginContext("oracle.test.kerberos.login", null, callback, loginConfig);
+            context.login();
+
+        } catch (LoginException ex) {
+            ex.printStackTrace();
+            throw new RuntimeException(ex);
+        }
+
+
+        Subject subject = context.getSubject();
+
+        final PrivilegedExceptionAction<Object> test_action = new PrivilegedExceptionAction<Object>() {
+            public Object run() throws Exception {
+                testConnect();
+                return null;
+            }
+        };
+
+        System.err.println("\n\nExpecting to succeed when executing with the the logged in subject.");
+
+        try {
+            Subject.doAs(subject, test_action);
+            System.err.println("\n\nConnection succeed when executing with the the logged in subject.");
+        } catch (PrivilegedActionException e) {
+            System.err.println("\n\nFailure unexpected when executing with the the logged in subject.");
+            e.printStackTrace();
+            throw new RuntimeException("Failed to login as subject");
+        }
+
+        try {
+            System.err.println("\n\nExpecting to fail when running with the current user's login.");
+            testConnect();
+        } catch (Exception ex) {
+            System.err.println("\nConnect failed when running with the current user's login:\n" + ex.getMessage());
+        }
+    }
+
     /**
      * Creates and starts an HTTP or proxy server that requires
      * Negotiate authentication.
@@ -366,3 +501,22 @@
         }
     }
 }
+
+class SecurityPolicy extends Policy {
+
+    private static Permissions perms;
+
+    public SecurityPolicy() {
+        super();
+        if (perms == null) {
+            perms = new Permissions();
+            perms.add(new AllPermission());
+        }
+    }
+
+    @Override
+    public PermissionCollection getPermissions(CodeSource codesource) {
+        return perms;
+    }
+
+}
--- a/jdk/test/sun/security/krb5/config/ConfPlusProp.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/sun/security/krb5/config/ConfPlusProp.java	Wed Jul 05 20:35:10 2017 +0200
@@ -35,6 +35,12 @@
 public class ConfPlusProp {
     Config config;
     public static void main(String[] args) throws Exception {
+        if (System.getenv("USERDNSDOMAIN") != null ||
+                System.getenv("LOGONSERVER") != null) {
+            System.out.println(
+                    "Looks like a Windows machine in a domain. Skip test.");
+            return;
+        }
         new ConfPlusProp().run();
     }
 
@@ -90,23 +96,8 @@
         check("R2", "old");
         check("R3", null);
 
-        int version = System.getProperty("java.version").charAt(2) - '0';
-        System.out.println("JDK version is " + version);
-
-        // Zero-config is supported since 1.7
-        if (version >= 7) {
-            // Point to a non-existing file
-            System.setProperty("java.security.krb5.conf", "i-am-not-a file");
-            refresh();
-
-            // Default realm might come from DNS
-            //checkDefaultRealm(null);
-            check("R1", null);
-            check("R2", null);
-            check("R3", null);
-            if (config.get("libdefaults", "forwardable") != null) {
-                throw new Exception("Extra config error");
-            }
+        if (config.get("libdefaults", "forwardable") != null) {
+            throw new Exception("Extra config error");
         }
 
         // Add prop
@@ -136,14 +127,6 @@
         check("R2", "k2");
         check("R3", "k2");
 
-        // Point to a non-existing file
-        System.setProperty("java.security.krb5.conf", "i-am-not-a file");
-        refresh();
-
-        checkDefaultRealm("R2");
-        check("R1", "k2");
-        check("R2", "k2");
-        check("R3", "k2");
         if (config.get("libdefaults", "forwardable") != null) {
             throw new Exception("Extra config error");
         }
--- a/jdk/test/sun/security/krb5/config/DNS.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/sun/security/krb5/config/DNS.java	Wed Jul 05 20:35:10 2017 +0200
@@ -23,12 +23,22 @@
 
 // See dns.sh.
 import sun.security.krb5.Config;
+import sun.security.krb5.KrbException;
 
 public class DNS {
     public static void main(String[] args) throws Exception {
         System.setProperty("java.security.krb5.conf",
-                System.getProperty("test.src", ".") +"/nothing.conf");
+                System.getProperty("test.src", ".") +"/no-such-file.conf");
         Config config = Config.getInstance();
+        try {
+            String r = config.getDefaultRealm();
+            throw new Exception("What? There is a default realm " + r + "?");
+        } catch (KrbException ke) {
+            ke.printStackTrace();
+            if (ke.getCause() != null) {
+                throw new Exception("There should be no cause. Won't try DNS");
+            }
+        }
         String kdcs = config.getKDCList("X");
         if (!kdcs.equals("a.com.:88 b.com.:99") &&
                 !kdcs.equals("a.com. b.com.:99")) {
--- a/jdk/test/sun/security/krb5/config/DnsFallback.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/sun/security/krb5/config/DnsFallback.java	Wed Jul 05 20:35:10 2017 +0200
@@ -22,8 +22,7 @@
  */
 /*
  * @test
- * @bug 6673164
- * @bug 6552334
+ * @bug 6673164 6552334 8077102
  * @run main/othervm DnsFallback
  * @summary fix dns_fallback parse error, and use dns by default
  */
@@ -35,47 +34,66 @@
 public class DnsFallback {
 
     static Method useDNS_Realm;
+    static Method useDNS_KDC;
 
     public static void main(String[] args) throws Exception {
 
         useDNS_Realm = Config.class.getDeclaredMethod("useDNS_Realm");
         useDNS_Realm.setAccessible(true);
+        useDNS_KDC = Config.class.getDeclaredMethod("useDNS_KDC");
+        useDNS_KDC.setAccessible(true);
 
 
         // for 6673164
-        check("true", "true", true);
-        check("false", "true", false);
-        check("true", "false", true);
-        check("false", "false", false);
-        check("true", null, true);
-        check("false", null, false);
-        check(null, "true", true);
-        check(null, "false", false);
+        check("true", "true", true, true);
+        check("false", "true", false, false);
+        check("true", "false", true, true);
+        check("false", "false", false, false);
+        check("true", null, true, true);
+        check("false", null, false, false);
+        check(null, "true", true, true);
+        check(null, "false", false, false);
 
-        // for 6552334
-        check(null, null, true);
+        // for 6552334, no longer true
+        //check(null, null, true, true);
+
+        // 8077102
+        check(null, null, false, true);
     }
 
-    static void check(String realm, String fallback, boolean output)
+    /**
+     * Sets and checks.
+     *
+     * @param u dns_lookup_XXX value set, none if null
+     * @param f dns_fallback value set, none if null
+     * @param r expected useDNS_Realm
+     * @param k expected useDNS_KDC
+     */
+    static void check(String u, String f, boolean r, boolean k)
             throws Exception {
 
         try (PrintStream ps =
                 new PrintStream(new FileOutputStream("dnsfallback.conf"))) {
             ps.println("[libdefaults]\n");
-            if (realm != null) {
-                ps.println("dns_lookup_realm=" + realm);
+            if (u != null) {
+                ps.println("dns_lookup_realm=" + u);
+                ps.println("dns_lookup_kdc=" + u);
             }
-            if (fallback != null) {
-                ps.println("dns_fallback=" + fallback);
+            if (f != null) {
+                ps.println("dns_fallback=" + f);
             }
         }
 
         System.setProperty("java.security.krb5.conf", "dnsfallback.conf");
         Config.refresh();
-        System.out.println("Testing " + realm + ", " + fallback + ", " + output);
+        System.out.println("Testing " + u + ", " + f + ", " + r + ", " + k);
 
-        if (!useDNS_Realm.invoke(Config.getInstance()).equals(output)) {
-            throw new Exception("Fail");
+        if (!useDNS_Realm.invoke(Config.getInstance()).equals(r)) {
+            throw new Exception("useDNS_Realm Fail");
+        }
+
+        if (!useDNS_KDC.invoke(Config.getInstance()).equals(k)) {
+            throw new Exception("useDNS_KDC Fail");
         }
     }
 }
--- a/jdk/test/sun/security/krb5/config/confplusprop.conf	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/sun/security/krb5/config/confplusprop.conf	Wed Jul 05 20:35:10 2017 +0200
@@ -1,7 +1,7 @@
 [libdefaults]
 default_realm = R1
 forwardable = well
-dns_lookup_realm = false
+dns_lookup_kdc = false
 
 [realms]
 R1 = {
--- a/jdk/test/sun/security/krb5/config/confplusprop2.conf	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/sun/security/krb5/config/confplusprop2.conf	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 [libdefaults]
-dns_lookup_realm = false
+dns_lookup_kdc = false
 
 [realms]
 R1 = {
--- a/jdk/test/sun/tools/common/ApplicationSetup.sh	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,210 +0,0 @@
-#!/bin/sh
-
-#
-# Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
-# 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.
-#
-
-
-# Support functions to start, stop, wait for or kill a given SimpleApplication
-
-# Starts a given app as background process, usage:
-#   startApplication <class> port-file [args...]
-#
-# The following variables are set:
-#
-# appJavaPid  - application's Java pid
-# appOtherPid - pid associated with the app other than appJavaPid
-# appPidList  - all pids associated with the app
-# appOutput   - file containing stdout and stderr from the app
-#
-# Waits for at least one line of output from the app to indicate
-# that it is up and running.
-#
-startApplication()
-{
-  appOutput="${TESTCLASSES}/Application.out"
-
-  ${JAVA} -XX:+UsePerfData -classpath "${TESTCLASSPATH:-${TESTCLASSES}}" "$@" > "$appOutput" 2>&1 &
-  appJavaPid="$!"
-  appOtherPid=
-  appPidList="$appJavaPid"
-
-  echo "INFO: waiting for $1 to initialize..."
-  _cnt=0
-  while true; do
-    # if the app doesn't start then the JavaTest/JTREG timeout will
-    # kick in so this isn't really a endless loop
-    sleep 1
-    out=`tail -1 "$appOutput"`
-    if [ -n "$out" ]; then
-      # we got some output from the app so it's running
-      break
-    fi
-    _cnt=`expr $_cnt + 1`
-    echo "INFO: waited $_cnt second(s) ..."
-  done
-  unset _cnt
-
-  if $isWindows; then
-    # Windows requires special handling
-    appOtherPid="$appJavaPid"
-
-    if $isCygwin; then
-      appJavaPid=`ps -p "$appOtherPid" \
-        | sed -n '
-          # See if $appOtherPid is in PID column; there are sometimes
-          # non-blanks in column 1 (I and S observed so far)
-          /^.'"${PATTERN_WS}${PATTERN_WS}*${appOtherPid}${PATTERN_WS}"'/{
-            # strip PID column
-            s/^.'"${PATTERN_WS}${PATTERN_WS}*${appOtherPid}${PATTERN_WS}${PATTERN_WS}"'*//
-            # strip PPID column
-            s/^[1-9][0-9]*'"${PATTERN_WS}${PATTERN_WS}"'*//
-            # strip PGID column
-            s/^[1-9][0-9]*'"${PATTERN_WS}${PATTERN_WS}"'*//
-            # strip everything after WINPID column
-            s/'"${PATTERN_WS}"'.*//
-            p
-            q
-          }
-        '`
-      echo "INFO: Cygwin pid=$appOtherPid maps to Windows pid=$appJavaPid"
-    else
-      # show PID, PPID and COMM columns only
-      appJavaPid=`ps -o pid,ppid,comm \
-        | sed -n '
-          # see if appOtherPid is in either PID or PPID columns
-          /'"${PATTERN_WS}${appOtherPid}${PATTERN_WS}"'/{
-            # see if this is a java command
-            /java'"${PATTERN_EOL}"'/{
-              # strip leading white space
-              s/^'"${PATTERN_WS}${PATTERN_WS}"'*//
-              # strip everything after the first word
-              s/'"${PATTERN_WS}"'.*//
-              # print the pid and we are done
-              p
-              q
-            }
-          }
-        '`
-      echo "INFO: MKS shell pid=$appOtherPid; Java pid=$appJavaPid"
-    fi
-
-    if [ -z "$appJavaPid" ]; then
-      echo "ERROR: could not find app's Java pid." >&2
-      killApplication
-      exit 2
-    fi
-    appPidList="$appOtherPid $appJavaPid"
-  fi
-
-  echo "INFO: $1 is process $appJavaPid"
-  echo "INFO: $1 output is in $appOutput"
-}
-
-
-# Stops a simple application by invoking ShutdownSimpleApplication
-# class with a specific port-file, usage:
-#   stopApplication port-file
-#
-# Note: When this function returns, the SimpleApplication (or a subclass)
-# may still be running because the application has not yet reached the
-# shutdown check.
-#
-stopApplication()
-{
-  $JAVA -XX:+UsePerfData -classpath "${TESTCLASSPATH:-${TESTCLASSES}}" ShutdownSimpleApplication $1
-}
-
-
-# Wait for a simple application to stop running.
-#
-waitForApplication() {
-  if [ $isWindows = false ]; then
-    # non-Windows is easy; just one process
-    echo "INFO: waiting for $appJavaPid"
-    set +e
-    wait "$appJavaPid"
-    set -e
-
-  elif $isCygwin; then
-    # Cygwin pid and not the Windows pid
-    echo "INFO: waiting for $appOtherPid"
-    set +e
-    wait "$appOtherPid"
-    set -e
-
-  else # implied isMKS
-    # MKS has intermediate shell and Java process
-    echo "INFO: waiting for $appJavaPid"
-
-    # appJavaPid can be empty if pid search in startApplication() failed
-    if [ -n "$appJavaPid" ]; then
-      # only need to wait for the Java process
-      set +e
-      wait "$appJavaPid"
-      set -e
-    fi
-  fi
-}
-
-
-# Kills a simple application by sending a SIGTERM to the appropriate
-# process(es); on Windows SIGQUIT (-9) is used.
-#
-killApplication()
-{
-  if [ $isWindows = false ]; then
-    # non-Windows is easy; just one process
-    echo "INFO: killing $appJavaPid"
-    set +e
-    kill -TERM "$appJavaPid"  # try a polite SIGTERM first
-    sleep 2
-    # send SIGQUIT (-9) just in case SIGTERM didn't do it
-    # but don't show any complaints
-    kill -QUIT "$appJavaPid" > /dev/null 2>&1
-    wait "$appJavaPid"
-    set -e
-
-  elif $isCygwin; then
-    # Cygwin pid and not the Windows pid
-    echo "INFO: killing $appOtherPid"
-    set +e
-    kill -9 "$appOtherPid"
-    wait "$appOtherPid"
-    set -e
-
-  else # implied isMKS
-    # MKS has intermediate shell and Java process
-    echo "INFO: killing $appPidList"
-    set +e
-    kill -9 $appPidList
-    set -e
-
-    # appJavaPid can be empty if pid search in startApplication() failed
-    if [ -n "$appJavaPid" ]; then
-      # only need to wait for the Java process
-      set +e
-      wait "$appJavaPid"
-      set -e
-    fi
-  fi
-}
--- a/jdk/test/sun/tools/common/CommonSetup.sh	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,131 +0,0 @@
-#!/bin/sh
-
-#
-# Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
-# 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.
-#
-
-
-# Common setup for tool tests and other tests that use jtools.
-# Checks that TESTJAVA, TESTSRC, and TESTCLASSES environment variables are set.
-#
-# Creates the following constants for use by the caller:
-#   JAVA        - java launcher
-#   JHAT        - jhat utility
-#   JINFO       - jinfo utility
-#   JMAP        - jmap utility
-#   JPS         - jps utility
-#   JSTACK      - jstack utility
-#   JCMD        - jcmd utility
-#   OS          - operating system name
-#   PATTERN_EOL - grep or sed end-of-line pattern
-#   PATTERN_WS  - grep or sed whitespace pattern
-#   PS          - path separator (";" or ":")
-#
-# Sets the following variables:
-#
-#   isCygwin  - true if environment is Cygwin
-#   isMKS     - true if environment is MKS
-#   isLinux   - true if OS is Linux
-#   isSolaris - true if OS is Solaris
-#   isWindows - true if OS is Windows
-#   isMacos   - true if OS is Macos X
-#   isAIX     - true if OS is AIX
-
-
-if [ -z "${TESTJAVA}" ]; then
-  echo "ERROR: TESTJAVA not set.  Test cannot execute.  Failed."
-  exit 1
-fi
-
-if [ -z "${TESTSRC}" ]; then
-  echo "ERROR: TESTSRC not set.  Test cannot execute.  Failed."
-  exit 1
-fi
-
-if [ -z "${TESTCLASSES}" ]; then
-  echo "ERROR: TESTCLASSES not set.  Test cannot execute.  Failed."
-  exit 1
-fi
-
-# only enable these after checking the expected incoming env variables
-set -eu
-
-JAVA="${TESTJAVA}/bin/java"
-JHAT="${TESTJAVA}/bin/jhat"
-JINFO="${TESTJAVA}/bin/jinfo"
-JMAP="${TESTJAVA}/bin/jmap"
-JPS="${TESTJAVA}/bin/jps"
-JSTACK="${TESTJAVA}/bin/jstack"
-JCMD="${TESTJAVA}/bin/jcmd"
-
-isCygwin=false
-isMKS=false
-isLinux=false
-isSolaris=false
-isUnknownOS=false
-isWindows=false
-isMacos=false
-isAIX=false
-
-OS=`uname -s`
-
-# start with some UNIX like defaults
-PATTERN_EOL='$'
-# blank and tab
-PATTERN_WS='[ 	]'
-PS=":"
-
-case "$OS" in
-  CYGWIN* )
-    OS="Windows"
-    PATTERN_EOL='[
]*$'
-    # blank and tab
-    PATTERN_WS='[ \t]'
-    isCygwin=true
-    isWindows=true
-    ;;
-  Linux )
-    OS="Linux"
-    isLinux=true
-    ;;
-  Darwin )
-    OS="Mac OS X"
-    isMacos=true
-    ;;
-  SunOS )
-    OS="Solaris"
-    isSolaris=true
-    ;;
-  AIX )
-    OS="AIX"
-    isAIX=true
-    ;;
-  Windows* )
-    OS="Windows"
-    PATTERN_EOL='[
]*$'
-    PS=";"
-    isWindows=true
-    ;;
-  * )
-    isUnknownOS=true
-    ;;
-esac
--- a/jdk/test/sun/tools/common/ShutdownSimpleApplication.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,76 +0,0 @@
-/*
- * Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-/*
- * Used to shutdown SimpleApplication (or a subclass). The argument to
- * this class is the name of a file that contains the TCP port number
- * on which SimpleApplication (or a subclass) is listening.
- *
- * Note: When this program returns, the SimpleApplication (or a subclass)
- * may still be running because the application has not yet reached the
- * shutdown check.
- */
-import java.net.Socket;
-import java.net.InetSocketAddress;
-import java.io.File;
-import java.io.FileInputStream;
-
-public class ShutdownSimpleApplication {
-    public static void main(String args[]) throws Exception {
-
-        if (args.length != 1) {
-            throw new RuntimeException("Usage: ShutdownSimpleApplication" +
-                " port-file");
-        }
-
-        // read the (TCP) port number from the given file
-
-        File f = new File(args[0]);
-        FileInputStream fis = new FileInputStream(f);
-        byte b[] = new byte[8];
-        int n = fis.read(b);
-        if (n < 1) {
-            throw new RuntimeException("Empty port-file");
-        }
-        fis.close();
-
-        String str = new String(b, 0, n, "UTF-8");
-        System.out.println("INFO: Port number of SimpleApplication: " + str);
-        int port = Integer.parseInt(str);
-
-        // Now connect to the port (which will shutdown application)
-
-        System.out.println("INFO: Connecting to port " + port +
-            " to shutdown SimpleApplication ...");
-        System.out.flush();
-
-        Socket s = new Socket();
-        s.connect( new InetSocketAddress(port) );
-        s.close();
-
-        System.out.println("INFO: done connecting to SimpleApplication.");
-        System.out.flush();
-
-        System.exit(0);
-    }
-}
--- a/jdk/test/sun/tools/common/SimpleApplication.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,120 +0,0 @@
-/*
- * Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-/*
- * A simple application used by unit tests. The first argument to this
- * class is the name of a file to which a TCP port number can be written.
- *
- * By default, this class does nothing other than bind to a TCP port,
- * write the TCP port number to a file, and wait for an incoming connection
- * in order to complete the application shutdown protocol.
- */
-import java.net.Socket;
-import java.net.ServerSocket;
-import java.io.File;
-import java.io.FileOutputStream;
-
-public class SimpleApplication {
-    private static SimpleApplication myApp;      // simple app or a subclass
-    private static String            myAppName;  // simple app name
-    private static int               myPort;     // coordination port #
-    private static ServerSocket      mySS;       // coordination socket
-
-    // protected so a subclass can extend it; not public so creation is
-    // limited.
-    protected SimpleApplication() {
-        // save simple app (or subclass) name for messages
-        myAppName = getClass().getName();
-    }
-
-    // return the simple application (or a subclass)
-    final public static SimpleApplication getMyApp() {
-        return myApp;
-    }
-
-    // set the simple application (for use by a subclass)
-    final public static void setMyApp(SimpleApplication _myApp) {
-        myApp = _myApp;
-    }
-
-    // execute the application finish protocol
-    final public void doMyAppFinish(String[] args) throws Exception {
-        System.out.println("INFO: " + myAppName + " is waiting on port: " +
-            myPort);
-        System.out.flush();
-
-        // wait for test harness to connect
-        Socket s = mySS.accept();
-        s.close();
-        mySS.close();
-
-        System.out.println("INFO: " + myAppName + " is shutting down.");
-        System.out.flush();
-    }
-
-    // execute the application start protocol
-    final public void doMyAppStart(String[] args) throws Exception {
-        if (args.length < 1) {
-            throw new RuntimeException("Usage: " + myAppName +
-                " port-file [arg(s)]");
-        }
-
-        // bind to a random port
-        mySS = new ServerSocket(0);
-        myPort = mySS.getLocalPort();
-
-        // Write the port number to the given file
-        File f = new File(args[0]);
-        FileOutputStream fos = new FileOutputStream(f);
-        fos.write( Integer.toString(myPort).getBytes("UTF-8") );
-        fos.close();
-
-        System.out.println("INFO: " + myAppName + " created socket on port: " +
-            myPort);
-        System.out.flush();
-    }
-
-    // execute the app work (subclass can override this)
-    public void doMyAppWork(String[] args) throws Exception {
-    }
-
-    public static void main(String[] args) throws Exception {
-        if (myApp == null) {
-            // create myApp since a subclass hasn't done so
-            myApp = new SimpleApplication();
-        }
-
-        myApp.doMyAppStart(args);   // do the app start protocol
-
-        System.out.println("INFO: " + myAppName + " is calling doMyAppWork()");
-        System.out.flush();
-        myApp.doMyAppWork(args);    // do the app work
-        System.out.println("INFO: " + myAppName + " returned from" +
-            " doMyAppWork()");
-        System.out.flush();
-
-        myApp.doMyAppFinish(args);  // do the app finish protocol
-
-        System.exit(0);
-    }
-}
--- a/jdk/test/sun/tools/common/SleeperApplication.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,59 +0,0 @@
-/*
- * Copyright (c) 2010, Oracle and/or its affiliates. All rights reserved.
- * 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.
- */
-
-/*
- * An example subclass of SimpleApplication that illustrates how to
- * override the doMyAppWork() method.
- */
-
-public class SleeperApplication extends SimpleApplication {
-    public static int DEFAULT_SLEEP_TIME = 60;  // time is in seconds
-
-    // execute the sleeper app work
-    public void doMyAppWork(String[] args) throws Exception {
-        int sleep_time = DEFAULT_SLEEP_TIME;
-
-        // args[0] is the port-file
-        if (args.length < 2) {
-            System.out.println("INFO: using default sleep time of "
-                + sleep_time + " seconds.");
-        } else {
-            try {
-                sleep_time = Integer.parseInt(args[1]);
-            } catch (NumberFormatException nfe) {
-                throw new RuntimeException("Error: '" + args[1] +
-                    "': is not a valid seconds value.");
-            }
-        }
-
-        Thread.sleep(sleep_time * 1000);  // our "work" is to sleep
-    }
-
-    public static void main(String[] args) throws Exception {
-        SleeperApplication myApp = new SleeperApplication();
-
-        SimpleApplication.setMyApp(myApp);
-
-        SimpleApplication.main(args);
-    }
-}
--- a/jdk/test/sun/tools/jhat/HatHeapDump1Test.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,89 +0,0 @@
-/*
- * 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
- * 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.util.Arrays;
-
-import jdk.testlibrary.Asserts;
-import jdk.testlibrary.JDKToolLauncher;
-import jdk.testlibrary.OutputAnalyzer;
-import jdk.testlibrary.ProcessTools;
-
-/* @test
- * @bug 5102009
- * @summary Sanity test of jhat functionality
- * @library /lib/testlibrary
- * @modules java.management
- * @build jdk.testlibarary.*
- * @compile -g HelloWorld.java
- * @run main HatHeapDump1Test
- */
-public class HatHeapDump1Test {
-
-    private static final String TEST_CLASSES = System.getProperty("test.classes", ".");
-
-    public static void main(String args[]) throws Exception {
-        String className = "HelloWorld";
-        File dumpFile = new File(className + ".hdump");
-
-        // Generate a heap dump
-        ProcessBuilder processBuilder = ProcessTools.createJavaProcessBuilder("-cp",
-                TEST_CLASSES,
-                "-Xcheck:jni",
-                "-Xverify:all",
-                "-agentlib:hprof=heap=dump,format=b,file=" + dumpFile.getAbsolutePath(),
-                className);
-        OutputAnalyzer output = ProcessTools.executeProcess(processBuilder);
-        System.out.println(output.getOutput());
-        output.shouldHaveExitValue(0);
-        output.shouldContain("Dumping Java heap ... done");
-        Asserts.assertTrue(dumpFile.exists() && dumpFile.isFile(), "Invalid dump file " + dumpFile.getAbsolutePath());
-
-        // Run jhat to analyze the heap dump
-        output = jhat("-debug", "2", dumpFile.getAbsolutePath());
-        output.shouldHaveExitValue(0);
-        output.shouldContain("Snapshot resolved");
-        output.shouldContain("-debug 2 was used");
-        output.shouldNotContain("ERROR");
-
-        dumpFile.delete();
-    }
-
-    private static OutputAnalyzer jhat(String... toolArgs) throws Exception {
-        JDKToolLauncher launcher = JDKToolLauncher.createUsingTestJDK("jhat");
-        if (toolArgs != null) {
-            for (String toolArg : toolArgs) {
-                launcher.addToolArg(toolArg);
-            }
-        }
-
-        ProcessBuilder processBuilder = new ProcessBuilder();
-        processBuilder.command(launcher.getCommand());
-        System.out.println(Arrays.toString(processBuilder.command().toArray()).replace(",", ""));
-        OutputAnalyzer output = ProcessTools.executeProcess(processBuilder);
-        System.out.println(output.getOutput());
-
-        return output;
-    }
-
-}
--- a/jdk/test/sun/tools/jhat/HelloWorld.java	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,51 +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.
- *
- * 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.
- */
-
-
-/*
- *
- *   Sample target application.
- *
- */
-
-public class HelloWorld {
-    public static void main(String args[]) {
-
-        /* Use a generic type */
-        java.util.List<String> l = new java.util.ArrayList<String>();
-        String.format("%s", "");
-
-        /* Just some code with branches */
-        try {
-            if ( args.length == 0 ) {
-                System.out.println("No arguments passed in");
-            } else {
-                System.out.println("Some arguments passed in");
-            }
-        } catch ( Throwable e ) {
-            System.out.println("ERROR: System.out.println() did a throw");
-        } finally {
-            System.out.println("Hello, world!");
-        }
-    }
-}
--- a/jdk/test/sun/tools/jhat/ParseTest.sh	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,69 +0,0 @@
-#!/bin/sh
-
-#
-# Copyright (c) 2006, 2010, Oracle and/or its affiliates. All rights reserved.
-# 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
-# @summary Testing jhat parsing against pre-created dump files.
-# see also: README.TXT
-
-# @library ../common
-# @run shell ParseTest.sh
-
-. ${TESTSRC}/../common/CommonSetup.sh
-
-# all return statuses are checked in this test
-set +e
-
-failed=0
-
-DUMPFILE="minimal.bin"
-
-${JHAT} -parseonly true ${TESTSRC}/${DUMPFILE}
-if [ $? != 0 ]; then failed=1; fi
-
-DUMPFILE="jmap.bin"
-
-${JHAT} -parseonly true ${TESTSRC}/${DUMPFILE}
-if [ $? != 0 ]; then failed=1; fi
-
-DUMPFILE="hprof.bin"
-
-${JHAT} -parseonly true ${TESTSRC}/${DUMPFILE}
-if [ $? != 0 ]; then failed=1; fi
-
-# try something that is not heapdump and expect to fail!
-DUMPFILE="ParseTest.sh"
-
-${JHAT} -parseonly true ${TESTSRC}/${DUMPFILE}
-if [ $? = 0 ]; then failed=1; fi
-
-# try something that does not exist and expect to fail!
-DUMPFILE="FileThatDoesNotExist"
-
-${JHAT} -parseonly true ${TESTSRC}/${DUMPFILE}
-if [ $? = 0 ]; then failed=1; fi
-
-exit $failed
-
--- a/jdk/test/sun/tools/jhat/README.TXT	Thu May 21 10:07:37 2015 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,16 +0,0 @@
-#
-
-jhat heap dump parsing tests:
-
-There are three hprof binary format dump files in this directory.
-These dumps were created by jmap and hprof profiler against a
-simple infinite looping Java program.
-
-1. minimal.bin - minimal dump that has nothing! - not even java.lang.Class!
-  - This was created by java -Xrunhprof:format=b,heap=sites MainClass. 
-
-2. jmap.bin - created by jmap -dump option
-
-3. hprof.bin - created by java -Xrunhprof:heap=all,format=b MainClass
-
-We can run jhat -parseonly true <dump-file> against these dumps. 
--- a/jdk/test/sun/tools/jmap/BasicJMapTest.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/sun/tools/jmap/BasicJMapTest.java	Wed Jul 05 20:35:10 2017 +0200
@@ -21,10 +21,13 @@
  * questions.
  */
 
+import static jdk.testlibrary.Asserts.assertTrue;
+import static jdk.testlibrary.Asserts.fail;
+
 import java.io.File;
 import java.util.Arrays;
 
-import static jdk.testlibrary.Asserts.*;
+import jdk.test.lib.hprof.HprofParser;
 import jdk.testlibrary.JDKToolLauncher;
 import jdk.testlibrary.OutputAnalyzer;
 import jdk.testlibrary.ProcessTools;
@@ -34,8 +37,13 @@
  * @bug 6321286
  * @summary Unit test for jmap utility
  * @library /lib/testlibrary
+ * @library /../../test/lib/share/classes
  * @modules java.management
  * @build jdk.testlibrary.*
+ * @build jdk.test.lib.hprof.*
+ * @build jdk.test.lib.hprof.module.*
+ * @build jdk.test.lib.hprof.parser.*
+ * @build jdk.test.lib.hprof.utils.*
  * @run main BasicJMapTest
  */
 public class BasicJMapTest {
@@ -60,24 +68,38 @@
     }
 
     private static void testDump() throws Exception {
-        File dump = new File("java_pid$" + ProcessTools.getProcessId() + ".hprof");
-        OutputAnalyzer output = jmap("-dump:format=b,file=" + dump.getName());
-        output.shouldHaveExitValue(0);
-        output.shouldContain("Heap dump file created");
-        verifyDumpFile(dump);
+        dump(false);
     }
 
     private static void testDumpLive() throws Exception {
-        File dump = new File("java_pid$" + ProcessTools.getProcessId() + ".hprof");
-        OutputAnalyzer output = jmap("-dump:live,format=b,file=" + dump.getName());
+        dump(true);
+    }
+
+    private static void dump(boolean live) throws Exception {
+        File dump = new File("jmap.dump." + System.currentTimeMillis() + ".hprof");
+        if (dump.exists()) {
+            dump.delete();
+        }
+        OutputAnalyzer output;
+        if (live) {
+            output = jmap("-dump:live,format=b,file=" + dump.getName());
+        } else {
+            output = jmap("-dump:format=b,file=" + dump.getName());
+        }
         output.shouldHaveExitValue(0);
         output.shouldContain("Heap dump file created");
         verifyDumpFile(dump);
+        dump.delete();
     }
 
     private static void verifyDumpFile(File dump) {
-        assertTrue(dump.exists() && dump.isFile(), "Could not create dump file");
-        dump.delete();
+        assertTrue(dump.exists() && dump.isFile(), "Could not create dump file " + dump.getAbsolutePath());
+        try {
+            HprofParser.parse(dump);
+        } catch (Exception e) {
+            e.printStackTrace();
+            fail("Could not parse dump file " + dump.getAbsolutePath());
+        }
     }
 
     private static OutputAnalyzer jmap(String... toolArgs) throws Exception {
--- a/jdk/test/tools/launcher/Arrrghs.java	Thu May 21 10:07:37 2015 -0700
+++ b/jdk/test/tools/launcher/Arrrghs.java	Wed Jul 05 20:35:10 2017 +0200
@@ -24,7 +24,7 @@
 /**
  * @test
  * @bug 5030233 6214916 6356475 6571029 6684582 6742159 4459600 6758881 6753938
- *      6894719 6968053 7151434 7146424 8007333
+ *      6894719 6968053 7151434 7146424 8007333 8077822
  * @summary Argument parsing validation.
  * @compile -XDignore.symbol.file Arrrghs.java
  * @run main/othervm Arrrghs
@@ -304,6 +304,16 @@
             throw new RuntimeException("Error: compiling java wildcards");
         }
 
+        // test if javac (the command) can compile *.java with a vmoption
+        tr = doExec(javacCmd, "-cp", ".",
+                    "-J-showversion", "-J-Dsomeproperty=foo",
+                    libDir.getName() + File.separator + "*.java");
+        if (!tr.isOK()) {
+            System.out.println(tr);
+            throw new RuntimeException("Error: compiling java wildcards with vmoptions");
+        }
+
+
         // use the jar cmd to create jars using the ? wildcard
         File jarFoo = new File(libDir, "Foo.jar");
         tr = doExec(jarCmd, "cvf", jarFoo.getAbsolutePath(), "lib" + File.separator + "F?o.class");
--- a/make/Images.gmk	Thu May 21 10:07:37 2015 -0700
+++ b/make/Images.gmk	Wed Jul 05 20:35:10 2017 +0200
@@ -213,7 +213,6 @@
       jcmd.1 \
       jdb.1 \
       jdeps.1 \
-      jhat.1 \
       jinfo.1 \
       jmap.1 \
       jps.1 \
--- a/make/JrtfsJar.gmk	Thu May 21 10:07:37 2015 -0700
+++ b/make/JrtfsJar.gmk	Wed Jul 05 20:35:10 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
@@ -28,10 +28,20 @@
 include $(SPEC)
 include MakeBase.gmk
 include JavaCompilation.gmk
+include TextFileProcessing.gmk
+
+# This rule will be depended on due to the MANIFEST line
+$(eval $(call SetupTextFileProcessing, BUILD_JAVA_MANIFEST, \
+  SOURCE_FILES := $(JDK_TOPDIR)/make/data/mainmanifest/manifest.mf, \
+  OUTPUT_FILE := $(SUPPORT_OUTPUTDIR)/java-main-manifest.mf, \
+  REPLACEMENTS := \
+      @@RELEASE@@ => $(RELEASE) ; \
+      @@COMPANY_NAME@@ => $(COMPANY_NAME) , \
+))
 
 $(eval $(call SetupArchive,JRTFS_JAR, , \
     SRCS := $(BUILDTOOLS_OUTPUTDIR)/interim_jimage_classes, \
     JAR := $(SUPPORT_OUTPUTDIR)/jrt-fs.jar, \
-    MANIFEST := $(JDK_TOPDIR)/make/data/mainmanifest/manifest.mf))
+    MANIFEST := $(SUPPORT_OUTPUTDIR)/java-main-manifest.mf))
 
 all: $(JRTFS_JAR)
--- a/make/common/JavaCompilation.gmk	Thu May 21 10:07:37 2015 -0700
+++ b/make/common/JavaCompilation.gmk	Wed Jul 05 20:35:10 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
@@ -265,7 +265,7 @@
   endif
 
   # Include all variables of significance in the vardeps file
-  $1_VARDEPS := $(JAR) $$($1_JAR_CREATE_OPTIONS) $$($1_MANIFEST) $(RELEASE) $(COMPANY_NAME) \
+  $1_VARDEPS := $(JAR) $$($1_JAR_CREATE_OPTIONS) $$($1_MANIFEST) \
       $$($1_JARMAIN) $$($1_EXTRA_MANIFEST_ATTR)
   $1_VARDEPS_FILE := $$(call DependOnVariable, $1_VARDEPS, $$(dir $$($1_JAR))_the.$$($1_JARNAME).vardeps)
 
@@ -280,8 +280,7 @@
         # potential changes.
 	$$(if $$(filter $$($1_VARDEPS_FILE) $$($1_MANIFEST), $$?), \
 	  $$(if $$($1_MANIFEST), \
-	    $(SED) -e "s#@@RELEASE@@#$(RELEASE)#" \
-	        -e "s#@@COMPANY_NAME@@#$(COMPANY_NAME)#" $$($1_MANIFEST) > $$($1_MANIFEST_FILE) $$(NEWLINE) \
+	    $(CP) $$($1_MANIFEST) $$($1_MANIFEST_FILE) $$(NEWLINE) \
 	  , \
 	    $(RM) $$($1_MANIFEST_FILE) && $(TOUCH) $$($1_MANIFEST_FILE) $$(NEWLINE)) \
 	  $$(if $$($1_JARMAIN), \
--- a/make/jprt.properties	Thu May 21 10:07:37 2015 -0700
+++ b/make/jprt.properties	Wed Jul 05 20:35:10 2017 +0200
@@ -428,15 +428,6 @@
   windows_i586_6.2-*-default-hotspot_basicvmtest,                       \
   windows_x64_6.2-*-default-hotspot_basicvmtest
   
-my.make.rule.test.targets.hotspot.internalvmtests=			\
-  solaris_sparcv9_5.11-fastdebug-c2-hotspot_internalvmtests,		\
-  solaris_x64_5.11-fastdebug-c2-hotspot_internalvmtests,		\
-  linux_i586_2.6-fastdebug-c2-hotspot_internalvmtests,			\
-  linux_x64_2.6-fastdebug-c2-hotspot_internalvmtests,			\
-  macosx_x64_10.9-fastdebug-c2-hotspot_internalvmtests,			\
-  windows_i586_6.2-fastdebug-c2-hotspot_internalvmtests,		\
-  windows_x64_6.2-fastdebug-c2-hotspot_internalvmtests
-
 my.make.rule.test.targets.hotspot.reg.group=				\
   solaris_sparcv9_5.11-fastdebug-c2-GROUP,				\
   solaris_x64_5.11-fastdebug-c2-GROUP,					\
@@ -450,7 +441,6 @@
 
 # Hotspot jtreg tests
 my.make.rule.test.targets.hotspot.reg=						\
-  ${my.make.rule.test.targets.hotspot.reg.group:GROUP=hotspot_wbapitest},	\
   ${my.make.rule.test.targets.hotspot.reg.group:GROUP=hotspot_compiler_1},	\
   ${my.make.rule.test.targets.hotspot.reg.group:GROUP=hotspot_compiler_2},	\
   ${my.make.rule.test.targets.hotspot.reg.group:GROUP=hotspot_compiler_3},	\
@@ -466,7 +456,6 @@
 # Other Makefile based Hotspot tests
 my.make.rule.test.targets.hotspot.other=                                \
   ${my.make.rule.test.targets.hotspot.basicvmtests},                    \
-  ${my.make.rule.test.targets.hotspot.internalvmtests},                 \
   ${my.additional.make.rule.test.targets.hotspot.other}
 
 # All the makefile based tests to run
--- a/modules.xml	Thu May 21 10:07:37 2015 -0700
+++ b/modules.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -2,7 +2,7 @@
 
 <!--
 
-   Copyright (c) 2014, 2015 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
@@ -216,19 +216,19 @@
     </export>
     <export>
       <name>jdk.internal.jimage</name>
-      <to>jdk.dev</to> 
+      <to>jdk.dev</to>
     </export>
     <export>
       <name>jdk.internal.org.objectweb.asm</name>
+      <to>java.instrument</to>
       <to>jdk.jfr</to>
       <to>jdk.scripting.nashorn</to>
-      <to>java.instrument</to>
     </export>
     <export>
       <name>jdk.internal.org.objectweb.asm.commons</name>
+      <to>java.instrument</to>
       <to>jdk.jfr</to>
       <to>jdk.scripting.nashorn</to>
-      <to>java.instrument</to>
     </export>
     <export>
       <name>jdk.internal.org.objectweb.asm.signature</name>
@@ -236,19 +236,20 @@
     </export>
     <export>
       <name>jdk.internal.org.objectweb.asm.tree</name>
+      <to>java.instrument</to>
       <to>jdk.jfr</to>
-      <to>java.instrument</to>
     </export>
     <export>
       <name>jdk.internal.org.objectweb.asm.util</name>
+      <to>java.instrument</to>
       <to>jdk.jfr</to>
       <to>jdk.scripting.nashorn</to>
-      <to>java.instrument</to>
     </export>
     <export>
       <name>sun.misc</name>
       <to>java.corba</to>
       <to>java.desktop</to>
+      <to>java.instrument</to>
       <to>java.logging</to>
       <to>java.management</to>
       <to>java.naming</to>
@@ -266,6 +267,7 @@
       <to>jdk.jartool</to>
       <to>jdk.jconsole</to>
       <to>jdk.jvmstat</to>
+      <to>jdk.management.resource</to>
       <to>jdk.pack200</to>
       <to>jdk.security.auth</to>
       <to>jdk.security.jgss</to>
@@ -301,6 +303,7 @@
       <to>java.management</to>
       <to>jdk.crypto.pkcs11</to>
       <to>jdk.crypto.ucrypto</to>
+      <to>jdk.management.resource</to>
       <to>jdk.sctp</to>
     </export>
     <export>
@@ -311,11 +314,11 @@
     <export>
       <name>sun.reflect</name>
       <to>java.corba</to>
+      <to>java.instrument</to>
       <to>java.logging</to>
       <to>java.sql</to>
       <to>java.sql.rowset</to>
       <to>jdk.scripting.nashorn</to>
-      <to>java.instrument</to>
     </export>
     <export>
       <name>sun.reflect.annotation</name>
@@ -774,6 +777,7 @@
     <export>
       <name>jdk.internal.instrumentation</name>
       <to>jdk.jfr</to>
+      <to>jdk.management.resource</to>
     </export>
   </module>
   <module>
--- a/nashorn/.hgtags	Thu May 21 10:07:37 2015 -0700
+++ b/nashorn/.hgtags	Wed Jul 05 20:35:10 2017 +0200
@@ -298,3 +298,4 @@
 1b5604bc81a6161b1c3c9dd654cd1399474ae9ee jdk9-b62
 bc8e67bec2f92772c4a67e20e66a4f216207f0af jdk9-b63
 00df6e4fc75a83bdd958f9ef86d80e008c9ba967 jdk9-b64
+2054d01ae32649d3179e93d14108fdd6259c1c0d jdk9-b65
--- a/nashorn/make/build.xml	Thu May 21 10:07:37 2015 -0700
+++ b/nashorn/make/build.xml	Wed Jul 05 20:35:10 2017 +0200
@@ -469,7 +469,7 @@
     </testng>
   </target>
 
-  <target name="test" depends="test-pessimistic, test-optimistic"/>
+  <target name="test" depends="javadoc, test-pessimistic, test-optimistic"/>
 
   <target name="test-optimistic" depends="jar, -test-classes-all,-test-classes-single, check-testng, check-external-tests, compile-test, generate-policy-file" if="testng.available">
     <echo message="Running test suite in OPTIMISTIC mode..."/>
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/nashorn/samples/console.js	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,134 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ *   - Redistributions of source code must retain the above copyright
+ *     notice, this list of conditions and the following disclaimer.
+ *
+ *   - Redistributions in binary form must reproduce the above copyright
+ *     notice, this list of conditions and the following disclaimer in the
+ *     documentation and/or other materials provided with the distribution.
+ *
+ *   - Neither the name of Oracle nor the names of its
+ *     contributors may be used to endorse or promote products derived
+ *     from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
+ * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/**
+ * Simple Web Console-like support for Nashorn. In addition to
+ * Web console object methods, this console add methods of
+ * java.io.Console as well. Note:not all web console methods are 
+ * implemented but useful subset is implemented.
+ *
+ * See also: https://developer.mozilla.org/en/docs/Web/API/console
+ */
+
+
+if (typeof console == 'undefined') {
+
+(function() {
+    var LocalDateTime = Java.type("java.time.LocalDateTime");
+    var System = Java.type("java.lang.System");
+    var jconsole = System.console();
+
+    // add a new global variable called "console"
+    this.console = {
+    };
+
+    function addConsoleMethods() {
+        // expose methods of java.io.Console as an extension
+        var placeholder = "-*-";
+        // put a placeholder for each name from java.lang.Object
+        var objMethods = Object.bindProperties({}, new java.lang.Object());
+        for (var m in objMethods) {
+            console[m] = placeholder;
+        }
+
+        // bind only the methods of java.io.Console
+        // This bind will skip java.lang.Object methods as console
+        // has properties of same name.
+        Object.bindProperties(console, jconsole);
+
+        // Now, delete java.lang.Object methods
+        for (var m in console) {
+            if (console[m] == placeholder) {
+                delete console[m];
+            }
+        }
+    }
+
+    addConsoleMethods();
+
+    function consoleLog(type, msg) {
+        // print type of message, then time.
+        jconsole.format("%s [%s] ", type, LocalDateTime.now().toString());
+        if (typeof msg == 'string') {
+            jconsole.format(msg + "\n", Array.prototype.slice.call(arguments, 2));
+        } else {
+            // simple space separated values and newline at the end
+            var arr = Array.prototype.slice.call(arguments, 1);
+            jconsole.format("%s\n", arr.join(" "));
+        }
+    }
+
+    console.toString = function() "[object Console]";
+
+    // web console functions
+
+    console.assert = function(expr) {
+        if (! expr) {
+            arguments[0] = "Assertion Failed:"; 
+            consoleLog.apply(console, arguments);
+            // now, stack trace at the end
+            jconsole.format("%s\n", new Error().stack);
+        }
+    };
+
+    // dummy clear to avoid error!
+    console.clear = function() {};
+
+    var counter = {
+        get: function(label) {
+            if (! this[label]) {
+                return this[label] = 1;
+            } else {
+                return ++this[label];
+            }
+        }
+    };
+   
+    // counter 
+    console.count = function(label) {
+        label = label? String(label) : "<no label>";
+        jconsole.format("%s: %d\n",label, counter.get(label).intValue());
+    }
+
+    // logging
+    console.error = consoleLog.bind(jconsole, "ERROR");
+    console.info = consoleLog.bind(jconsole, "INFO");
+    console.log = console.info;
+    console.debug = console.log;
+    console.warn = consoleLog.bind(jconsole, "WARNING");
+
+    // print stack trace
+    console.trace = function() {
+        jconsole.format("%s\n", new Error().stack);
+    };
+})();
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/nashorn/samples/consoleuse.js	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,55 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ *   - Redistributions of source code must retain the above copyright
+ *     notice, this list of conditions and the following disclaimer.
+ *
+ *   - Redistributions in binary form must reproduce the above copyright
+ *     notice, this list of conditions and the following disclaimer in the
+ *     documentation and/or other materials provided with the distribution.
+ *
+ *   - Neither the name of Oracle nor the names of its
+ *     contributors may be used to endorse or promote products derived
+ *     from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
+ * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+load(__DIR__ + "console.js");
+
+console.log("consoleuse.js started!");
+
+function func() {
+    console.count("func");
+}
+
+
+func();
+func();
+func();
+func();
+
+// java.io.Console method
+console.readPassword("passworld please: ");
+console.error("Big error: %s!", "you revealed your password!");
+console.warn("You've done this %d times", 345);
+console.assert(arguments.length != 0, "no arguments!");
+
+// java.io.Console methods
+var str = console.readLine("enter something: ");
+console.printf("you entered: %s\n", str);
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/nashorn/samples/undefined_call.js	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,48 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ *   - Redistributions of source code must retain the above copyright
+ *     notice, this list of conditions and the following disclaimer.
+ *
+ *   - Redistributions in binary form must reproduce the above copyright
+ *     notice, this list of conditions and the following disclaimer in the
+ *     documentation and/or other materials provided with the distribution.
+ *
+ *   - Neither the name of Oracle nor the names of its
+ *     contributors may be used to endorse or promote products derived
+ *     from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
+ * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+// Nashorn extension: __noSuchMethod__
+// See also: https://wiki.openjdk.java.net/display/Nashorn/Nashorn+extensions#Nashornextensions-__noSuchMethod__
+ 
+Object.prototype.__noSuchMethod__ = function(name) {
+    print(name + " function is not defined in " + this);
+ 
+    // Nashorn extension: stack property
+    // gives stack trace as a string
+    print(new Error().stack);
+}
+ 
+function func(obj) {
+    obj.foo();
+}
+ 
+func({});
+func(this); 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/nashorn/samples/unzip.js	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,79 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ *   - Redistributions of source code must retain the above copyright
+ *     notice, this list of conditions and the following disclaimer.
+ *
+ *   - Redistributions in binary form must reproduce the above copyright
+ *     notice, this list of conditions and the following disclaimer in the
+ *     documentation and/or other materials provided with the distribution.
+ *
+ *   - Neither the name of Oracle nor the names of its
+ *     contributors may be used to endorse or promote products derived
+ *     from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
+ * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/*
+ * Simple unzip tool using #nashorn and #java
+ * zip fs file system interface.
+ */
+ 
+if (arguments.length == 0) {
+    print("Usage: jjs zipfs.js -- <.zip/.jar file> [out dir]");
+    exit(1);
+}
+ 
+var File = Java.type("java.io.File");
+// output directory where zip is extracted
+var outDir = arguments[1];
+if (!outDir) {
+    outDir = ".";
+} else {
+    if (! new File(outDir).isDirectory()) {
+        print(outDir + " directory does not exist!");
+        exit(1);
+    }
+}
+ 
+var Files = Java.type("java.nio.file.Files");
+var FileSystems = Java.type("java.nio.file.FileSystems");
+var Paths = Java.type("java.nio.file.Paths");
+ 
+var zipfile = Paths.get(arguments[0])
+var fs = FileSystems.newFileSystem(zipfile, null);
+var root = fs.rootDirectories[0];
+ 
+// walk root and handle each Path
+Files.walk(root).forEach(
+    function(p) {
+        var outPath = outDir +
+            p.toString().replace('/', File.separatorChar);
+        print(outPath);
+        if (Files.isDirectory(p)) {
+            // create directories as needed
+            new File(outPath).mkdirs();
+        } else {
+            // copy a 'file' resource
+            Files.copy(p, new File(outPath).toPath());
+        }
+    }
+);
+ 
+// done
+fs.close(); 
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/codegen/CodeGenerator.java	Thu May 21 10:07:37 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/codegen/CodeGenerator.java	Wed Jul 05 20:35:10 2017 +0200
@@ -3798,7 +3798,6 @@
             emitBranch(binaryNode, onTrue, true);
             if (isCurrentDiscard) {
                 method.label(onTrue);
-                method.pop();
             } else {
                 method.load(false);
                 method._goto(skip);
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/ir/LexicalContext.java	Thu May 21 10:07:37 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/ir/LexicalContext.java	Wed Jul 05 20:35:10 2017 +0200
@@ -204,7 +204,7 @@
     /**
      * Explicitly apply flags to the topmost element on the stack. This is only valid to use from a
      * {@code NodeVisitor.leaveXxx()} method and only on the node being exited at the time. It is not mandatory to use,
-     * as {@link #pop(LexicalContextNode)} will apply the flags automatically, but this method can be used to apply them
+     * as {@link #pop(Node)} will apply the flags automatically, but this method can be used to apply them
      * during the {@code leaveXxx()} method in case its logic depends on the value of the flags.
      * @param node the node to apply the flags to. Must be the topmost node on the stack.
      * @return the passed in node, or a modified node (if any flags were modified)
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/ir/TryNode.java	Thu May 21 10:07:37 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/ir/TryNode.java	Wed Jul 05 20:35:10 2017 +0200
@@ -57,7 +57,7 @@
      * block was not terminal; the original jump/return is simply ignored if the finally block itself
      * terminates). The reason for this somewhat strange arrangement is that we didn't want to create a
      * separate class for the (label, BlockStatement pair) but rather reused the already available LabelNode.
-     * However, if we simply used List<LabelNode> without wrapping the label nodes in an additional Block,
+     * However, if we simply used List&lt;LabelNode&gt; without wrapping the label nodes in an additional Block,
      * that would've thrown off visitors relying on BlockLexicalContext -- same reason why we never use
      * Statement as the type of bodies of e.g. IfNode, WhileNode etc. but rather blockify them even when they're
      * single statements.
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/objects/Global.java	Thu May 21 10:07:37 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/objects/Global.java	Wed Jul 05 20:35:10 2017 +0200
@@ -220,7 +220,12 @@
     @Property(name = "Number", attributes = Attribute.NOT_ENUMERABLE)
     public volatile Object number;
 
-    /** ECMA 15.1.4.7 Date constructor */
+    /**
+     * Getter for ECMA 15.1.4.7 Date property
+     *
+     * @param self self reference
+     * @return Date property value
+     */
     @Getter(name = "Date", attributes = Attribute.NOT_ENUMERABLE)
     public static Object getDate(final Object self) {
         final Global global = Global.instanceFrom(self);
@@ -230,6 +235,12 @@
         return global.date;
     }
 
+    /**
+     * Setter for ECMA 15.1.4.7 Date property
+     *
+     * @param self self reference
+     * @param value value for the Date property
+     */
     @Setter(name = "Date", attributes = Attribute.NOT_ENUMERABLE)
     public static void setDate(final Object self, final Object value) {
         final Global global = Global.instanceFrom(self);
@@ -238,7 +249,12 @@
 
     private volatile Object date = LAZY_SENTINEL;
 
-    /** ECMA 15.1.4.8 RegExp constructor */
+    /**
+     * Getter for ECMA 15.1.4.8 RegExp property
+     *
+     * @param self self reference
+     * @return RegExp property value
+     */
     @Getter(name = "RegExp", attributes = Attribute.NOT_ENUMERABLE)
     public static Object getRegExp(final Object self) {
         final Global global = Global.instanceFrom(self);
@@ -248,6 +264,12 @@
         return global.regexp;
     }
 
+    /**
+     * Setter for ECMA 15.1.4.8 RegExp property
+     *
+     * @param self self reference
+     * @param value value for the RegExp property
+     */
     @Setter(name = "RegExp", attributes = Attribute.NOT_ENUMERABLE)
     public static void setRegExp(final Object self, final Object value) {
         final Global global = Global.instanceFrom(self);
@@ -256,7 +278,11 @@
 
     private volatile Object regexp = LAZY_SENTINEL;
 
-    /** ECMA 15.12 - The JSON object */
+    /**
+     * Getter for ECMA 15.12 - The JSON property
+     * @param self self reference
+     * @return the value of JSON property
+     */
     @Getter(name = "JSON", attributes = Attribute.NOT_ENUMERABLE)
     public static Object getJSON(final Object self) {
         final Global global = Global.instanceFrom(self);
@@ -266,6 +292,11 @@
         return global.json;
     }
 
+    /**
+     * Setter for ECMA 15.12 - The JSON property
+     * @param self self reference
+     * @param value value for the JSON property
+     */
     @Setter(name = "JSON", attributes = Attribute.NOT_ENUMERABLE)
     public static void setJSON(final Object self, final Object value) {
         final Global global = Global.instanceFrom(self);
@@ -274,7 +305,11 @@
 
     private volatile Object json = LAZY_SENTINEL;
 
-    /** Nashorn extension: global.JSAdapter */
+    /**
+     * Getter for Nashorn extension: global.JSAdapter
+     * @param self self reference
+     * @return value of the JSAdapter property
+     */
     @Getter(name = "JSAdapter", attributes = Attribute.NOT_ENUMERABLE)
     public static Object getJSAdapter(final Object self) {
         final Global global = Global.instanceFrom(self);
@@ -284,6 +319,11 @@
         return global.jsadapter;
     }
 
+    /**
+     * Setter for Nashorn extension: global.JSAdapter
+     * @param self self reference
+     * @param value value for the JSAdapter property
+     */
     @Setter(name = "JSAdapter", attributes = Attribute.NOT_ENUMERABLE)
     public static void setJSAdapter(final Object self, final Object value) {
         final Global global = Global.instanceFrom(self);
@@ -300,7 +340,11 @@
     @Property(name = "Error", attributes = Attribute.NOT_ENUMERABLE)
     public volatile Object error;
 
-    /** EvalError object */
+    /**
+     * Getter for the EvalError property
+     * @param self self reference
+     * @return the value of EvalError property
+     */
     @Getter(name = "EvalError", attributes = Attribute.NOT_ENUMERABLE)
     public static Object getEvalError(final Object self) {
         final Global global = Global.instanceFrom(self);
@@ -310,6 +354,11 @@
         return global.evalError;
     }
 
+    /**
+     * Setter for the EvalError property
+     * @param self self reference
+     * @param value value of the EvalError property
+     */
     @Setter(name = "EvalError", attributes = Attribute.NOT_ENUMERABLE)
     public static void setEvalError(final Object self, final Object value) {
         final Global global = Global.instanceFrom(self);
@@ -318,7 +367,11 @@
 
     private volatile Object evalError = LAZY_SENTINEL;
 
-    /** RangeError object */
+    /**
+     * Getter for the RangeError property.
+     * @param self self reference
+     * @return the value of RangeError property
+     */
     @Getter(name = "RangeError", attributes = Attribute.NOT_ENUMERABLE)
     public static Object getRangeError(final Object self) {
         final Global global = Global.instanceFrom(self);
@@ -328,6 +381,12 @@
         return global.rangeError;
     }
 
+
+    /**
+     * Setter for the RangeError property.
+     * @param self self reference
+     * @param value value for the RangeError property
+     */
     @Setter(name = "RangeError", attributes = Attribute.NOT_ENUMERABLE)
     public static void setRangeError(final Object self, final Object value) {
         final Global global = Global.instanceFrom(self);
@@ -348,7 +407,11 @@
     @Property(name = "TypeError", attributes = Attribute.NOT_ENUMERABLE)
     public volatile Object typeError;
 
-    /** URIError object */
+    /**
+     * Getter for the URIError property.
+     * @param self self reference
+     * @return the value of URIError property
+     */
     @Getter(name = "URIError", attributes = Attribute.NOT_ENUMERABLE)
     public static Object getURIError(final Object self) {
         final Global global = Global.instanceFrom(self);
@@ -358,6 +421,11 @@
         return global.uriError;
     }
 
+    /**
+     * Setter for the URIError property.
+     * @param self self reference
+     * @param value value for the URIError property
+     */
     @Setter(name = "URIError", attributes = Attribute.NOT_ENUMERABLE)
     public static void setURIError(final Object self, final Object value) {
         final Global global = Global.instanceFrom(self);
@@ -366,7 +434,11 @@
 
     private volatile Object uriError = LAZY_SENTINEL;
 
-    /** ArrayBuffer object */
+    /**
+     * Getter for the ArrayBuffer property.
+     * @param self self reference
+     * @return the value of the ArrayBuffer property
+     */
     @Getter(name = "ArrayBuffer", attributes = Attribute.NOT_ENUMERABLE)
     public static Object getArrayBuffer(final Object self) {
         final Global global = Global.instanceFrom(self);
@@ -376,6 +448,11 @@
         return global.arrayBuffer;
     }
 
+    /**
+     * Setter for the ArrayBuffer property.
+     * @param self self reference
+     * @param value value of the ArrayBuffer property
+     */
     @Setter(name = "ArrayBuffer", attributes = Attribute.NOT_ENUMERABLE)
     public static void setArrayBuffer(final Object self, final Object value) {
         final Global global = Global.instanceFrom(self);
@@ -384,7 +461,11 @@
 
     private volatile Object arrayBuffer;
 
-    /** DataView object */
+    /**
+     * Getter for the DataView property.
+     * @param self self reference
+     * @return the value of the DataView property
+     */
     @Getter(name = "DataView", attributes = Attribute.NOT_ENUMERABLE)
     public static Object getDataView(final Object self) {
         final Global global = Global.instanceFrom(self);
@@ -394,6 +475,12 @@
         return global.dataView;
     }
 
+
+    /**
+     * Setter for the DataView property.
+     * @param self self reference
+     * @param value value of the DataView property
+     */
     @Setter(name = "DataView", attributes = Attribute.NOT_ENUMERABLE)
     public static void setDataView(final Object self, final Object value) {
         final Global global = Global.instanceFrom(self);
@@ -402,7 +489,11 @@
 
     private volatile Object dataView;
 
-    /** TypedArray (int8) */
+    /**
+     * Getter for the Int8Array property.
+     * @param self self reference
+     * @return the value of the Int8Array property.
+     */
     @Getter(name = "Int8Array", attributes = Attribute.NOT_ENUMERABLE)
     public static Object getInt8Array(final Object self) {
         final Global global = Global.instanceFrom(self);
@@ -412,6 +503,11 @@
         return global.int8Array;
     }
 
+    /**
+     * Setter for the Int8Array property.
+     * @param self self reference
+     * @param value value of the Int8Array property
+     */
     @Setter(name = "Int8Array", attributes = Attribute.NOT_ENUMERABLE)
     public static void setInt8Array(final Object self, final Object value) {
         final Global global = Global.instanceFrom(self);
@@ -420,7 +516,11 @@
 
     private volatile Object int8Array;
 
-    /** TypedArray (uint8) */
+    /**
+     * Getter for the Uin8Array property.
+     * @param self self reference
+     * @return the value of the Uint8Array property
+     */
     @Getter(name = "Uint8Array", attributes = Attribute.NOT_ENUMERABLE)
     public static Object getUint8Array(final Object self) {
         final Global global = Global.instanceFrom(self);
@@ -430,6 +530,11 @@
         return global.uint8Array;
     }
 
+    /**
+     * Setter for the Uin8Array property.
+     * @param self self reference
+     * @param value value of the Uin8Array property
+     */
     @Setter(name = "Uint8Array", attributes = Attribute.NOT_ENUMERABLE)
     public static void setUint8Array(final Object self, final Object value) {
         final Global global = Global.instanceFrom(self);
@@ -438,7 +543,11 @@
 
     private volatile Object uint8Array;
 
-    /** TypedArray (uint8) - Clamped */
+    /**
+     * Getter for the Uint8ClampedArray property.
+     * @param self self reference
+     * @return the value of the Uint8ClampedArray property
+     */
     @Getter(name = "Uint8ClampedArray", attributes = Attribute.NOT_ENUMERABLE)
     public static Object getUint8ClampedArray(final Object self) {
         final Global global = Global.instanceFrom(self);
@@ -448,6 +557,11 @@
         return global.uint8ClampedArray;
     }
 
+    /**
+     * Setter for the Uint8ClampedArray property.
+     * @param self self reference
+     * @param value value of the Uint8ClampedArray property
+     */
     @Setter(name = "Uint8ClampedArray", attributes = Attribute.NOT_ENUMERABLE)
     public static void setUint8ClampedArray(final Object self, final Object value) {
         final Global global = Global.instanceFrom(self);
@@ -456,7 +570,11 @@
 
     private volatile Object uint8ClampedArray;
 
-    /** TypedArray (int16) */
+    /**
+     * Getter for the Int16Array property.
+     * @param self self reference
+     * @return the value of the Int16Array property
+     */
     @Getter(name = "Int16Array", attributes = Attribute.NOT_ENUMERABLE)
     public static Object getInt16Array(final Object self) {
         final Global global = Global.instanceFrom(self);
@@ -466,6 +584,11 @@
         return global.int16Array;
     }
 
+    /**
+     * Setter for the Int16Array property.
+     * @param self self reference
+     * @param value value of the Int16Array property
+     */
     @Setter(name = "Int16Array", attributes = Attribute.NOT_ENUMERABLE)
     public static void setInt16Array(final Object self, final Object value) {
         final Global global = Global.instanceFrom(self);
@@ -474,7 +597,11 @@
 
     private volatile Object int16Array;
 
-    /** TypedArray (uint16) */
+    /**
+     * Getter for the Uint16Array property.
+     * @param self self reference
+     * @return the value of the Uint16Array property
+     */
     @Getter(name = "Uint16Array", attributes = Attribute.NOT_ENUMERABLE)
     public static Object getUint16Array(final Object self) {
         final Global global = Global.instanceFrom(self);
@@ -484,6 +611,11 @@
         return global.uint16Array;
     }
 
+    /**
+     * Setter for the Uint16Array property.
+     * @param self self reference
+     * @param value value of the Uint16Array property
+     */
     @Setter(name = "Uint16Array", attributes = Attribute.NOT_ENUMERABLE)
     public static void setUint16Array(final Object self, final Object value) {
         final Global global = Global.instanceFrom(self);
@@ -492,7 +624,12 @@
 
     private volatile Object uint16Array;
 
-    /** TypedArray (int32) */
+    /**
+     * Getter for the Int32Array property.
+     *
+     * @param self self reference
+     * @return the value of the Int32Array property
+     */
     @Getter(name = "Int32Array", attributes = Attribute.NOT_ENUMERABLE)
     public static Object getInt32Array(final Object self) {
         final Global global = Global.instanceFrom(self);
@@ -502,6 +639,13 @@
         return global.int32Array;
     }
 
+
+    /**
+     * Setter for the Int32Array property.
+     *
+     * @param self self reference
+     * @param value value of the Int32Array property
+     */
     @Setter(name = "Int32Array", attributes = Attribute.NOT_ENUMERABLE)
     public static void setInt32Array(final Object self, final Object value) {
         final Global global = Global.instanceFrom(self);
@@ -510,7 +654,12 @@
 
     private volatile Object int32Array;
 
-    /** TypedArray (uint32) */
+    /**
+     * Getter of the Uint32Array property.
+     *
+     * @param self self reference
+     * @return the value of the Uint32Array property
+     */
     @Getter(name = "Uint32Array", attributes = Attribute.NOT_ENUMERABLE)
     public static Object getUint32Array(final Object self) {
         final Global global = Global.instanceFrom(self);
@@ -520,6 +669,13 @@
         return global.uint32Array;
     }
 
+
+    /**
+     * Setter of the Uint32Array property.
+     *
+     * @param self self reference
+     * @param value value of the Uint32Array property
+     */
     @Setter(name = "Uint32Array", attributes = Attribute.NOT_ENUMERABLE)
     public static void setUint32Array(final Object self, final Object value) {
         final Global global = Global.instanceFrom(self);
@@ -528,7 +684,12 @@
 
     private volatile Object uint32Array;
 
-    /** TypedArray (float32) */
+    /**
+     * Getter for the Float32Array property.
+     *
+     * @param self self reference
+     * @return the value of the Float32Array property
+     */
     @Getter(name = "Float32Array", attributes = Attribute.NOT_ENUMERABLE)
     public static Object getFloat32Array(final Object self) {
         final Global global = Global.instanceFrom(self);
@@ -538,6 +699,12 @@
         return global.float32Array;
     }
 
+    /**
+     * Setter for the Float32Array property.
+     *
+     * @param self self reference
+     * @param value value of the Float32Array property
+     */
     @Setter(name = "Float32Array", attributes = Attribute.NOT_ENUMERABLE)
     public static void setFloat32Array(final Object self, final Object value) {
         final Global global = Global.instanceFrom(self);
@@ -546,7 +713,12 @@
 
     private volatile Object float32Array;
 
-    /** TypedArray (float64) */
+    /**
+     * Getter for the Float64Array property.
+     *
+     * @param self self reference
+     * @return the value of the Float64Array property
+     */
     @Getter(name = "Float64Array", attributes = Attribute.NOT_ENUMERABLE)
     public static Object getFloat64Array(final Object self) {
         final Global global = Global.instanceFrom(self);
@@ -556,6 +728,12 @@
         return global.float64Array;
     }
 
+    /**
+     * Setter for the Float64Array property.
+     *
+     * @param self self reference
+     * @param value value of the Float64Array property
+     */
     @Setter(name = "Float64Array", attributes = Attribute.NOT_ENUMERABLE)
     public static void setFloat64Array(final Object self, final Object value) {
         final Global global = Global.instanceFrom(self);
@@ -592,7 +770,12 @@
     @Property(attributes = Attribute.NOT_ENUMERABLE)
     public volatile Object org;
 
-    /** Nashorn extension: Java access - global.javaImporter */
+    /**
+     * Getter for the Nashorn extension: Java access - global.javaImporter.
+     *
+     * @param self self reference
+     * @return the value of the JavaImporter property
+     */
     @Getter(name = "JavaImporter", attributes = Attribute.NOT_ENUMERABLE)
     public static Object getJavaImporter(final Object self) {
         final Global global = Global.instanceFrom(self);
@@ -602,6 +785,12 @@
         return global.javaImporter;
     }
 
+    /**
+     * Setter for the Nashorn extension: Java access - global.javaImporter.
+     *
+     * @param self self reference
+     * @param value value of the JavaImporter property
+     */
     @Setter(name = "JavaImporter", attributes = Attribute.NOT_ENUMERABLE)
     public static void setJavaImporter(final Object self, final Object value) {
         final Global global = Global.instanceFrom(self);
@@ -610,7 +799,12 @@
 
     private volatile Object javaImporter;
 
-    /** Nashorn extension: global.Java Object constructor. */
+    /**
+     * Getter for the Nashorn extension: global.Java property.
+     *
+     * @param self self reference
+     * @return the value of the Java property
+     */
     @Getter(name = "Java", attributes = Attribute.NOT_ENUMERABLE)
     public static Object getJavaApi(final Object self) {
         final Global global = Global.instanceFrom(self);
@@ -620,6 +814,12 @@
         return global.javaApi;
     }
 
+    /**
+     * Setter for the Nashorn extension: global.Java property.
+     *
+     * @param self self reference
+     * @param value value of the Java property
+     */
     @Setter(name = "Java", attributes = Attribute.NOT_ENUMERABLE)
     public static void setJavaApi(final Object self, final Object value) {
         final Global global = Global.instanceFrom(self);
@@ -2139,13 +2339,13 @@
     @Override
     public void addBoundProperties(final ScriptObject source, final jdk.nashorn.internal.runtime.Property[] properties) {
         PropertyMap ownMap = getMap();
-        LexicalScope lexicalScope = null;
+        LexicalScope lexScope = null;
         PropertyMap lexicalMap = null;
         boolean hasLexicalDefinitions = false;
 
         if (context.getEnv()._es6) {
-            lexicalScope = (LexicalScope) getLexicalScope();
-            lexicalMap = lexicalScope.getMap();
+            lexScope = (LexicalScope) getLexicalScope();
+            lexicalMap = lexScope.getMap();
 
             for (final jdk.nashorn.internal.runtime.Property property : properties) {
                 if (property.isLexicalBinding()) {
@@ -2165,8 +2365,8 @@
 
         for (final jdk.nashorn.internal.runtime.Property property : properties) {
             if (property.isLexicalBinding()) {
-                assert lexicalScope != null;
-                lexicalMap = lexicalScope.addBoundProperty(lexicalMap, source, property);
+                assert lexScope != null;
+                lexicalMap = lexScope.addBoundProperty(lexicalMap, source, property);
 
                 if (ownMap.findProperty(property.getKey()) != null) {
                     // If property exists in the global object invalidate any global constant call sites.
@@ -2180,7 +2380,8 @@
         setMap(ownMap);
 
         if (hasLexicalDefinitions) {
-            lexicalScope.setMap(lexicalMap);
+            assert lexScope != null;
+            lexScope.setMap(lexicalMap);
             invalidateLexicalSwitchPoint();
         }
     }
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/objects/NativeObject.java	Thu May 21 10:07:37 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/objects/NativeObject.java	Wed Jul 05 20:35:10 2017 +0200
@@ -765,7 +765,7 @@
                 continue;
             }
             properties.add(AccessorProperty.create(methodName, Property.NOT_WRITABLE, getBoundBeanMethodGetter(source,
-                    method), null));
+                    method), Lookup.EMPTY_SETTER));
         }
         for(final String propertyName: propertyNames) {
             MethodHandle getter;
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/ScriptingFunctions.java	Thu May 21 10:07:37 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/ScriptingFunctions.java	Wed Jul 05 20:35:10 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
@@ -34,10 +34,13 @@
 import java.io.IOException;
 import java.io.InputStreamReader;
 import java.io.OutputStreamWriter;
+import java.io.StreamTokenizer;
+import java.io.StringReader;
 import java.lang.invoke.MethodHandle;
 import java.lang.invoke.MethodHandles;
+import java.util.ArrayList;
+import java.util.List;
 import java.util.Map;
-import java.util.StringTokenizer;
 
 /**
  * Global functions supported only in scripting mode.
@@ -133,15 +136,8 @@
         // Current global is need to fetch additional inputs and for additional results.
         final ScriptObject global = Context.getGlobal();
 
-        // Break exec string into tokens.
-        final StringTokenizer tokenizer = new StringTokenizer(JSType.toString(string));
-        final String[] cmdArray = new String[tokenizer.countTokens()];
-        for (int i = 0; tokenizer.hasMoreTokens(); i++) {
-            cmdArray[i] = tokenizer.nextToken();
-        }
-
         // Set up initial process.
-        final ProcessBuilder processBuilder = new ProcessBuilder(cmdArray);
+        final ProcessBuilder processBuilder = new ProcessBuilder(tokenizeCommandLine(JSType.toString(string)));
 
         // Current ENV property state.
         final Object env = global.get(ENV_NAME);
@@ -239,4 +235,43 @@
     private static MethodHandle findOwnMH(final String name, final Class<?> rtype, final Class<?>... types) {
         return MH.findStatic(MethodHandles.lookup(), ScriptingFunctions.class, name, MH.type(rtype, types));
     }
+
+    /**
+     * Break an exec string into tokens, honoring quoted arguments and escaped
+     * spaces.
+     *
+     * @param execString a {@link String} with the command line to execute.
+     * @return a {@link List} of {@link String}s representing the tokens that
+     * constitute the command line.
+     * @throws IOException in case {@link StreamTokenizer#nextToken()} raises it.
+     */
+    private static List<String> tokenizeCommandLine(final String execString) throws IOException {
+        final StreamTokenizer tokenizer = new StreamTokenizer(new StringReader(execString));
+        tokenizer.resetSyntax();
+        tokenizer.wordChars(0, 255);
+        tokenizer.whitespaceChars(0, ' ');
+        tokenizer.commentChar('#');
+        tokenizer.quoteChar('"');
+        tokenizer.quoteChar('\'');
+        final List<String> cmdList = new ArrayList<>();
+        final StringBuilder toAppend = new StringBuilder();
+        while (tokenizer.nextToken() != StreamTokenizer.TT_EOF) {
+            final String s = tokenizer.sval;
+            // The tokenizer understands about honoring quoted strings and recognizes
+            // them as one token that possibly contains multiple space-separated words.
+            // It does not recognize quoted spaces, though, and will split after the
+            // escaping \ character. This is handled here.
+            if (s.endsWith("\\")) {
+                // omit trailing \, append space instead
+                toAppend.append(s.substring(0, s.length() - 1)).append(' ');
+            } else {
+                cmdList.add(toAppend.append(s).toString());
+                toAppend.setLength(0);
+            }
+        }
+        if (toAppend.length() != 0) {
+            cmdList.add(toAppend.toString());
+        }
+        return cmdList;
+    }
 }
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/arrays/IntArrayData.java	Thu May 21 10:07:37 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/arrays/IntArrayData.java	Wed Jul 05 20:35:10 2017 +0200
@@ -182,14 +182,13 @@
 
     @Override
     public ArrayData convert(final Class<?> type) {
-        if (type == Integer.class) {
+        if (type == Integer.class || type == Byte.class || type == Short.class) {
             return this;
         } else if (type == Long.class) {
             return convertToLong();
-        } else if (type == Double.class) {
+        } else if (type == Double.class || type == Float.class) {
             return convertToDouble();
         } else {
-            assert type == null || (!Number.class.isAssignableFrom(type) && !type.isPrimitive());
             return convertToObject();
         }
     }
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/arrays/LongArrayData.java	Thu May 21 10:07:37 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/arrays/LongArrayData.java	Wed Jul 05 20:35:10 2017 +0200
@@ -120,11 +120,11 @@
 
     @Override
     public ContinuousArrayData convert(final Class<?> type) {
-        if (type == Integer.class || type == Long.class) {
+        if (type == Integer.class || type == Long.class || type == Byte.class || type == Short.class) {
             return this;
         }
         final int len = (int)length();
-        if (type == Double.class) {
+        if (type == Double.class || type == Float.class) {
             return new NumberArrayData(toDoubleArray(), len);
         }
         return new ObjectArrayData(toObjectArray(false), len);
@@ -171,7 +171,8 @@
 
     @Override
     public ArrayData set(final int index, final Object value, final boolean strict) {
-        if (value instanceof Long || value instanceof Integer) {
+        if (value instanceof Long || value instanceof Integer ||
+            value instanceof Byte || value instanceof Short) {
             return set(index, ((Number)value).longValue(), strict);
         } else if (value == ScriptRuntime.UNDEFINED) {
             return new UndefinedArrayFilter(this).set(index, value, strict);
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/arrays/NumberArrayData.java	Thu May 21 10:07:37 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/arrays/NumberArrayData.java	Wed Jul 05 20:35:10 2017 +0200
@@ -29,6 +29,7 @@
 import static jdk.nashorn.internal.lookup.Lookup.MH;
 import static jdk.nashorn.internal.runtime.ScriptRuntime.UNDEFINED;
 
+import jdk.internal.dynalink.support.TypeUtilities;
 import java.lang.invoke.MethodHandle;
 import java.lang.invoke.MethodHandles;
 import java.util.Arrays;
@@ -104,9 +105,14 @@
         return super.asArrayOfType(componentType);
     }
 
+    private static boolean canWiden(final Class<?> type) {
+        return TypeUtilities.isWrapperType(type) &&
+            type != Boolean.class && type != Character.class;
+    }
+
     @Override
     public ContinuousArrayData convert(final Class<?> type) {
-        if (type != Double.class && type != Integer.class && type != Long.class) {
+        if (! canWiden(type)) {
             final int len = (int)length();
             return new ObjectArrayData(toObjectArray(false), len);
         }
@@ -154,7 +160,7 @@
 
     @Override
     public ArrayData set(final int index, final Object value, final boolean strict) {
-        if (value instanceof Double || value instanceof Integer || value instanceof Long) {
+        if (value instanceof Double || (value != null && canWiden(value.getClass()))) {
             return set(index, ((Number)value).doubleValue(), strict);
         } else if (value == UNDEFINED) {
             return new UndefinedArrayFilter(this).set(index, value, strict);
--- a/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/linker/NashornLinker.java	Thu May 21 10:07:37 2015 -0700
+++ b/nashorn/src/jdk.scripting.nashorn/share/classes/jdk/nashorn/internal/runtime/linker/NashornLinker.java	Wed Jul 05 20:35:10 2017 +0200
@@ -216,10 +216,11 @@
         // Could've also used (targetType.isAssignableFrom(ScriptObjectMirror.class) && targetType != Object.class) but
         // it's probably better to explicitly spell out the supported target types
         if (targetType == Map.class || targetType == Bindings.class || targetType == JSObject.class || targetType == ScriptObjectMirror.class) {
-            if(ScriptObject.class.isAssignableFrom(sourceType)) {
+            if (ScriptObject.class.isAssignableFrom(sourceType)) {
                 return new GuardedInvocation(CREATE_MIRROR);
+            } else if (sourceType.isAssignableFrom(ScriptObject.class) || sourceType.isInterface()) {
+                return new GuardedInvocation(CREATE_MIRROR, IS_SCRIPT_OBJECT);
             }
-            return new GuardedInvocation(CREATE_MIRROR, IS_SCRIPT_OBJECT);
         }
         return null;
     }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/nashorn/test/script/basic/JDK-8079145.js	Wed Jul 05 20:35:10 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-8079145: jdk.nashorn.internal.runtime.arrays.IntArrayData.convert assertion
+ *
+ * @test
+ * @fork
+ * @option -Dnashorn.debug=true
+ * @run
+ */
+
+var Byte = java.lang.Byte;
+var Short = java.lang.Short;
+var Integer = java.lang.Integer;
+var Long = java.lang.Long;
+var Float = java.lang.Float;
+var Double = java.lang.Double;
+var Character = java.lang.Character;
+
+function checkWiden(arr, value, name) {
+    switch (typeof value) {
+    case 'object':
+    case 'undefined':
+        print(name + ": check widen for " + value);
+        break;
+    default:
+        print(name + ": check widen for " + value + 
+            " [" + Debug.getClass(value) + "]");
+    }
+
+    arr[0] = value;
+}
+
+function checkIntWiden(value) {
+   checkWiden([34], value, "int array");
+}
+
+function checkLongWiden(value) {
+    checkWiden([Integer.MAX_VALUE + 1], value, "long array");
+}
+
+function checkNumberWiden(value) {
+    checkWiden([Math.PI], value, "number array");
+}
+
+function checkObjectWiden(value) {
+    checkWiden([null], value, "object array");
+}
+
+var values = [{}, null, undefined, false, true, new Byte(34),
+   new Integer(344454), new Long(454545), new Long(Integer.MAX_VALUE + 1),
+   new Float(34.3), new Double(Math.PI), new Character('s')];
+
+for each (var v in values) {
+    checkIntWiden(v);
+}
+
+for each (var v in values) {
+    checkLongWiden(v);
+}
+
+for each (var v in values) {
+    checkNumberWiden(v);
+}
+
+for each (var v in values) {
+    checkObjectWiden(v);
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/nashorn/test/script/basic/JDK-8079145.js.EXPECTED	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,48 @@
+int array: check widen for [object Object]
+int array: check widen for null
+int array: check widen for undefined
+int array: check widen for false [class java.lang.Boolean]
+int array: check widen for true [class java.lang.Boolean]
+int array: check widen for 34 [class java.lang.Byte]
+int array: check widen for 344454 [class java.lang.Integer]
+int array: check widen for 454545 [class java.lang.Long]
+int array: check widen for 2147483648 [class java.lang.Long]
+int array: check widen for 34.29999923706055 [class java.lang.Float]
+int array: check widen for 3.141592653589793 [class java.lang.Double]
+int array: check widen for s
+long array: check widen for [object Object]
+long array: check widen for null
+long array: check widen for undefined
+long array: check widen for false [class java.lang.Boolean]
+long array: check widen for true [class java.lang.Boolean]
+long array: check widen for 34 [class java.lang.Byte]
+long array: check widen for 344454 [class java.lang.Integer]
+long array: check widen for 454545 [class java.lang.Long]
+long array: check widen for 2147483648 [class java.lang.Long]
+long array: check widen for 34.29999923706055 [class java.lang.Float]
+long array: check widen for 3.141592653589793 [class java.lang.Double]
+long array: check widen for s
+number array: check widen for [object Object]
+number array: check widen for null
+number array: check widen for undefined
+number array: check widen for false [class java.lang.Boolean]
+number array: check widen for true [class java.lang.Boolean]
+number array: check widen for 34 [class java.lang.Byte]
+number array: check widen for 344454 [class java.lang.Integer]
+number array: check widen for 454545 [class java.lang.Long]
+number array: check widen for 2147483648 [class java.lang.Long]
+number array: check widen for 34.29999923706055 [class java.lang.Float]
+number array: check widen for 3.141592653589793 [class java.lang.Double]
+number array: check widen for s
+object array: check widen for [object Object]
+object array: check widen for null
+object array: check widen for undefined
+object array: check widen for false [class java.lang.Boolean]
+object array: check widen for true [class java.lang.Boolean]
+object array: check widen for 34 [class java.lang.Byte]
+object array: check widen for 344454 [class java.lang.Integer]
+object array: check widen for 454545 [class java.lang.Long]
+object array: check widen for 2147483648 [class java.lang.Long]
+object array: check widen for 34.29999923706055 [class java.lang.Float]
+object array: check widen for 3.141592653589793 [class java.lang.Double]
+object array: check widen for s
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/nashorn/test/script/basic/JDK-8079424.js	Wed Jul 05 20:35:10 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.
+ */
+
+/**
+ * JDK-8079424: code generator for discarded boolean logical operation has an extra pop
+ *
+ * @test
+ * @run
+ */
+
+// If the compiler manages to compile all of these, the test passes.
+void (true && true);
+void (true && false);
+void (false && true);
+void (false && false);
+
+void (true || true);
+void (true || false);
+void (false || true);
+void (false || false);
+
+void (1 && 1);
+void (1 && 0);
+void (0 && 1);
+void (0 && 0);
+
+void (1 || 1);
+void (1 || 0);
+void (0 || 1);
+void (0 || 0);
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/nashorn/test/script/basic/JDK-8080848.js	Wed Jul 05 20:35:10 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.
+ * 
+ * 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-8080848: delete of bound Java method property results in crash
+ *
+ * @test
+ * @run
+ */
+
+var obj = Object.bindProperties({}, new java.io.File("."));
+
+delete obj.wait;
+
+if (typeof obj.wait != 'undefined') {
+    throw new Error("obj.wait was not deleted");
+}
--- a/nashorn/test/script/nosecurity/JDK-8050964.js	Thu May 21 10:07:37 2015 -0700
+++ b/nashorn/test/script/nosecurity/JDK-8050964.js	Wed Jul 05 20:35:10 2017 +0200
@@ -47,9 +47,9 @@
 }
 
 var javahome = System.getProperty("java.home");
-var jdepsPath = javahome + "/../bin/jdeps".replaceAll(/\//g, File.separater);
+var jdepsPath = javahome + "/../bin/jdeps".replace(/\//g, File.separator);
 if (! new File(jdepsPath).isFile()) {
-    jdepsPath = javahome + "/bin/jdeps".replaceAll(/\//g, File.separater);
+    jdepsPath = javahome + "/bin/jdeps".replace(/\//g, File.separator);
 }
 
 // run jdep on nashorn.jar - only summary but print profile info
--- a/nashorn/test/script/nosecurity/JDK-8055034.js	Thu May 21 10:07:37 2015 -0700
+++ b/nashorn/test/script/nosecurity/JDK-8055034.js	Wed Jul 05 20:35:10 2017 +0200
@@ -46,10 +46,10 @@
 
 // we want to use nashorn.jar passed and not the one that comes with JRE
 var jjsCmd = javahome + "/../bin/jjs";
-jjsCmd = jjsCmd.toString().replaceAll(/\//g, File.separater);
+jjsCmd = jjsCmd.toString().replace(/\//g, File.separator);
 if (! new File(jjsCmd).isFile()) {
     jjsCmd = javahome + "/bin/jjs";
-    jjsCmd = jjsCmd.toString().replaceAll(/\//g, File.separater);
+    jjsCmd = jjsCmd.toString().replace(/\//g, File.separator);
 }
 jjsCmd += " -J-Xbootclasspath/p:" + nashornJar;
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/nashorn/test/src/jdk/nashorn/internal/runtime/test/JDK_8078414_Test.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,99 @@
+/*
+ * 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.nashorn.internal.runtime.test;
+
+import static org.testng.Assert.assertFalse;
+import static org.testng.Assert.assertTrue;
+
+import java.util.Map;
+import javax.script.Bindings;
+import jdk.nashorn.api.scripting.JSObject;
+import jdk.nashorn.api.scripting.ScriptObjectMirror;
+import jdk.nashorn.internal.objects.NativeArray;
+import jdk.nashorn.internal.runtime.ScriptObject;
+import jdk.nashorn.internal.runtime.linker.Bootstrap;
+import org.testng.annotations.Test;
+
+/**
+ * @test
+ * @bug 8078414
+ * @summary Test that arbitrary classes can't be converted to mirror's superclasses/interfaces.
+ * @run testng jdk.nashorn.internal.runtime.test.JDK_8078414_Test
+ */
+public class JDK_8078414_Test {
+    @Test
+    public void testCanNotConvertArbitraryClassToMirror() {
+        assertCanNotConvert(Double.class, Map.class);
+        assertCanNotConvert(Double.class, Bindings.class);
+        assertCanNotConvert(Double.class, JSObject.class);
+        assertCanNotConvert(Double.class, ScriptObjectMirror.class);
+    }
+
+    @Test
+    public void testCanConvertObjectToMirror() {
+        assertCanConvertToMirror(Object.class);
+    }
+
+    @Test
+    public void testCanConvertScriptObjectToMirror() {
+        assertCanConvertToMirror(ScriptObject.class);
+    }
+
+    @Test
+    public void testCanConvertScriptObjectSubclassToMirror() {
+        assertCanConvertToMirror(NativeArray.class);
+    }
+
+    @Test
+    public void testCanConvertArbitraryInterfaceToMirror() {
+        // We allow arbitrary interface classes, depending on what implements them, to end up being
+        // convertible to ScriptObjectMirror, as an implementation can theoretically pass an
+        // "instanceof ScriptObject" guard.
+        assertCanConvertToMirror(TestInterface.class);
+    }
+
+    public static interface TestInterface {
+    }
+
+    private static boolean canConvert(final Class<?> from, final Class<?> to) {
+        return Bootstrap.getLinkerServices().canConvert(from, to);
+    }
+
+    private static void assertCanConvert(final Class<?> from, final Class<?> to) {
+        assertTrue(canConvert(from, to));
+    }
+
+    private static void assertCanNotConvert(final Class<?> from, final Class<?> to) {
+        assertFalse(canConvert(from, to));
+    }
+
+    private static void assertCanConvertToMirror(final Class<?> from) {
+        assertCanConvert(from, Map.class);
+        assertCanConvert(from, Bindings.class);
+        assertCanConvert(from, JSObject.class);
+        assertCanConvert(from, ScriptObjectMirror.class);
+    }
+}
--- a/test/lib/Makefile	Thu May 21 10:07:37 2015 -0700
+++ b/test/lib/Makefile	Wed Jul 05 20:35:10 2017 +0200
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2013, 2014, 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
@@ -41,25 +41,38 @@
 JAVAC = $(JDK_HOME)/bin/javac
 JAR = $(JDK_HOME)/bin/jar
 
-SRC_FILES = $(shell find $(SRC_DIR) -name '*.java')
+WB_SRC_FILES = $(shell find $(SRC_DIR)/sun/hotspot -name '*.java')
+SHARE_SRC_FILES = $(shell find $(SRC_DIR)/share/classes -name '*.java')
 
-.PHONY: filelist clean cleantmp
+.PHONY: wb.filelist share.filelist clean cleantmp
 
-all: wb.jar cleantmp
+all: wb.jar test-lib.jar cleantmp
 
-wb.jar: filelist
+wb.jar: wb.filelist
 	@mkdir -p $(OUTPUT_DIR)
-	$(JAVAC) -sourcepath $(SRC_DIR) -d $(OUTPUT_DIR) -cp $(OUTPUT_DIR) @filelist
+	$(JAVAC) -sourcepath $(SRC_DIR) -d $(OUTPUT_DIR) -cp $(OUTPUT_DIR) @wb.filelist
 	$(JAR) cf wb.jar -C $(OUTPUT_DIR) .
 	@rm -rf $(OUTPUT_DIR)
 
-filelist: $(SRC_FILES)
+wb.filelist: $(WB_SRC_FILES)
 	@rm -f $@
-	@echo $(SRC_FILES) > $@
+	@echo $(WB_SRC_FILES) > $@
+
+test-lib.jar: share.filelist
+	@mkdir -p $(OUTPUT_DIR)
+	$(JAVAC) -sourcepath $(SRC_DIR) -d $(OUTPUT_DIR) -cp $(OUTPUT_DIR) @share.filelist
+	$(JAR) cf test-lib.jar -C $(OUTPUT_DIR) .
+	@rm -rf $(OUTPUT_DIR)
+
+share.filelist: $(SHARE_SRC_FILES)
+	@rm -f $@
+	@echo $(SHARE_SRC_FILES) > $@
 
 clean: cleantmp
 	@rm -rf wb.jar
+	@rm -rf test-list.jar
 
 cleantmp:
-	@rm -rf filelist
+	@rm -rf wb.filelist
+	@rm -rf share.filelist
 	@rm -rf $(BUILD_DIR)
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/HprofParser.java	Wed Jul 05 20:35:10 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.
+ */
+
+package jdk.test.lib.hprof;
+
+import java.io.BufferedOutputStream;
+import java.io.File;
+import java.io.FileOutputStream;
+import java.io.PrintStream;
+
+import jdk.test.lib.hprof.model.Snapshot;
+import jdk.test.lib.hprof.parser.Reader;
+
+/**
+ * Helper class to parse a java heap dump file.
+ */
+public class HprofParser {
+
+    public static void main(String[] args) throws Exception {
+        if (args.length < 1) {
+            System.out.println("No arguments supplied");
+        }
+        File dump = new File(args[0]);
+        if (!dump.exists() || !dump.isFile()) {
+            throw new RuntimeException("The dump file does not exist or not a file");
+        }
+        parse(dump);
+    }
+
+    /**
+     * @see #parse(File, boolean, boolean, boolean)
+     */
+    public static File parse(File dump) throws Exception {
+        return parse(dump, false, true, true);
+    }
+
+    /**
+     * @see #parse(File, boolean, boolean, boolean)
+     */
+    public static File parseWithDebugInfo(File dump) throws Exception {
+        return parse(dump, true, true, true);
+    }
+
+    /**
+     * Parse a java heap dump file
+     *
+     * @param dump Heap dump file to parse
+     * @param debug Turn on/off debug file parsing
+     * @param callStack Turn on/off tracking of object allocation call stack
+     * @param calculateRefs Turn on/off tracking object allocation call stack
+     * @throws Exception
+     * @return File containing output from the parser
+     */
+    public static File parse(File dump, boolean debug, boolean callStack, boolean calculateRefs) throws Exception {
+        File out = new File("hprof." + System.currentTimeMillis() + ".out");
+        if (out.exists()) {
+            out.delete();
+        }
+
+        PrintStream psSystemOut = System.out;
+        try (PrintStream psHprof = new PrintStream(new BufferedOutputStream(new FileOutputStream(out.getAbsolutePath())))) {
+            System.setOut(psHprof);
+
+            int debugLevel = debug ? 2 : 0;
+            try (Snapshot snapshot = Reader.readFile(dump.getAbsolutePath(), callStack, debugLevel)) {
+                System.out.println("Snapshot read, resolving...");
+                snapshot.resolve(calculateRefs);
+                System.out.println("Snapshot resolved.");
+            }
+       } finally {
+           System.setOut(psSystemOut);
+       }
+
+        return out;
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/README	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,13 @@
+The jhat tool has been removed. jhat hprof file parser/validator
+are needed for tests. The old packages for jhat were moved here:
+com.sun.tools.hat.internal.model -> jdk.test.lib.hprof.model
+com.sun.tools.hat.internal.parser -> jdk.test.lib.hprof.parser
+com.sun.tools.hat.internal.util -> jdk.test.lib.hprof.util
+ 
+jhat was added in JDK 6 and its original implementation was from 
+java.net HAT project [1]. jhat is an experimental, unsupported tool. 
+There hasn't been much update to jhat tool in the JDK. In addition, 
+there are several better heap dump visualizer/analyzer emerged since 
+JDK 5/6 serviceability support.
+
+[1] https://java.net/projects/hat
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/AbstractJavaHeapObjectVisitor.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,60 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+/**
+ * A visitor for a JavaThing.  @see JavaObject#visitReferencedObjects()
+ *
+ */
+
+
+abstract public class AbstractJavaHeapObjectVisitor
+                implements JavaHeapObjectVisitor {
+    abstract public void visit(JavaHeapObject other);
+
+    /**
+     * Should the given field be excluded from the set of things visited?
+     * @return true if it should.
+     */
+    public boolean exclude(JavaClass clazz, JavaField f) {
+        return false;
+    }
+
+    /**
+     * @return true iff exclude might ever return true
+     */
+    public boolean mightExclude() {
+        return false;
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/ArrayTypeCodes.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,50 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+/**
+ * Primitive array type codes as defined by VM specification.
+ *
+ */
+public interface ArrayTypeCodes {
+    // Typecodes for array elements.
+    // Refer to newarray instruction in VM Spec.
+    public static final int T_BOOLEAN = 4;
+    public static final int T_CHAR    = 5;
+    public static final int T_FLOAT   = 6;
+    public static final int T_DOUBLE  = 7;
+    public static final int T_BYTE    = 8;
+    public static final int T_SHORT   = 9;
+    public static final int T_INT     = 10;
+    public static final int T_LONG    = 11;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/HackJavaValue.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,65 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+/**
+ * This is used to represent values that the program doesn't really understand.
+ * This includes the null vlaue, and unresolved references (which shouldn't
+ * happen in well-formed hprof files).
+ *
+ *
+ * @author      Bill Foote
+ */
+
+
+
+
+public class HackJavaValue extends JavaValue {
+
+    private String value;
+    private int size;
+
+    public HackJavaValue(String value, int size) {
+        this.value = value;
+        this.size = size;
+    }
+
+    public String toString() {
+        return value;
+    }
+
+    public int getSize() {
+        return size;
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/JavaBoolean.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,54 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+/**
+ * Represents a boolean (i.e. a boolean field in an instance).
+ *
+ * @author      Bill Foote
+ */
+
+
+public class JavaBoolean extends JavaValue {
+
+    boolean value;
+
+    public JavaBoolean(boolean value) {
+        this.value = value;
+    }
+
+    public String toString() {
+        return "" + value;
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/JavaByte.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,54 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+/**
+ * Represents an byte (i.e. a byte field in an instance).
+ *
+ * @author      Bill Foote
+ */
+
+
+public class JavaByte extends JavaValue {
+
+    byte value;
+
+    public JavaByte(byte value) {
+        this.value = value;
+    }
+
+    public String toString() {
+        return "0x" + Integer.toString(((int) value) & 0xff, 16);
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/JavaChar.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,54 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+/**
+ * Represents a char (i.e. a char field in an instance).
+ *
+ * @author      Bill Foote
+ */
+
+
+public class JavaChar extends JavaValue {
+
+    char value;
+
+    public JavaChar(char value) {
+        this.value = value;
+    }
+
+    public String toString() {
+        return "" + value;
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/JavaClass.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,503 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+import java.util.Vector;
+import java.util.Enumeration;
+import jdk.test.lib.hprof.util.CompositeEnumeration;
+import jdk.test.lib.hprof.parser.ReadBuffer;
+
+/**
+ *
+ * @author      Bill Foote
+ */
+
+
+public class JavaClass extends JavaHeapObject {
+    // my id
+    private long id;
+    // my name
+    private String name;
+
+    // These are JavaObjectRef before resolve
+    private JavaThing superclass;
+    private JavaThing loader;
+    private JavaThing signers;
+    private JavaThing protectionDomain;
+
+    // non-static fields
+    private JavaField[] fields;
+    // static fields
+    private JavaStatic[] statics;
+
+    private static final JavaClass[] EMPTY_CLASS_ARRAY = new JavaClass[0];
+    // my subclasses
+    private JavaClass[] subclasses = EMPTY_CLASS_ARRAY;
+
+    // my instances
+    private Vector<JavaHeapObject> instances = new Vector<JavaHeapObject>();
+
+    // Who I belong to.  Set on resolve.
+    private Snapshot mySnapshot;
+
+    // Size of an instance, including VM overhead
+    private int instanceSize;
+    // Total number of fields including inherited ones
+    private int totalNumFields;
+
+
+    public JavaClass(long id, String name, long superclassId, long loaderId,
+                     long signersId, long protDomainId,
+                     JavaField[] fields, JavaStatic[] statics,
+                     int instanceSize) {
+        this.id = id;
+        this.name = name;
+        this.superclass = new JavaObjectRef(superclassId);
+        this.loader = new JavaObjectRef(loaderId);
+        this.signers = new JavaObjectRef(signersId);
+        this.protectionDomain = new JavaObjectRef(protDomainId);
+        this.fields = fields;
+        this.statics = statics;
+        this.instanceSize = instanceSize;
+    }
+
+    public JavaClass(String name, long superclassId, long loaderId,
+                     long signersId, long protDomainId,
+                     JavaField[] fields, JavaStatic[] statics,
+                     int instanceSize) {
+        this(-1L, name, superclassId, loaderId, signersId,
+             protDomainId, fields, statics, instanceSize);
+    }
+
+    public final JavaClass getClazz() {
+        return mySnapshot.getJavaLangClass();
+    }
+
+    public final int getIdentifierSize() {
+        return mySnapshot.getIdentifierSize();
+    }
+
+    public final int getMinimumObjectSize() {
+        return mySnapshot.getMinimumObjectSize();
+    }
+
+    public void resolve(Snapshot snapshot) {
+        if (mySnapshot != null) {
+            return;
+        }
+        mySnapshot = snapshot;
+        resolveSuperclass(snapshot);
+        if (superclass != null) {
+            ((JavaClass) superclass).addSubclass(this);
+        }
+
+        loader  = loader.dereference(snapshot, null);
+        signers  = signers.dereference(snapshot, null);
+        protectionDomain  = protectionDomain.dereference(snapshot, null);
+
+        for (int i = 0; i < statics.length; i++) {
+            statics[i].resolve(this, snapshot);
+        }
+        snapshot.getJavaLangClass().addInstance(this);
+        super.resolve(snapshot);
+        return;
+    }
+
+    /**
+     * Resolve our superclass.  This might be called well before
+     * all instances are available (like when reading deferred
+     * instances in a 1.2 dump file :-)  Calling this is sufficient
+     * to be able to explore this class' fields.
+     */
+    public void resolveSuperclass(Snapshot snapshot) {
+        if (superclass == null) {
+            // We must be java.lang.Object, so we have no superclass.
+        } else {
+            totalNumFields = fields.length;
+            superclass = superclass.dereference(snapshot, null);
+            if (superclass == snapshot.getNullThing()) {
+                superclass = null;
+            } else {
+                try {
+                    JavaClass sc = (JavaClass) superclass;
+                    sc.resolveSuperclass(snapshot);
+                    totalNumFields += sc.totalNumFields;
+                } catch (ClassCastException ex) {
+                    System.out.println("Warning!  Superclass of " + name + " is " + superclass);
+                    superclass = null;
+                }
+            }
+        }
+    }
+
+    public boolean isString() {
+        return mySnapshot.getJavaLangString() == this;
+    }
+
+    public boolean isClassLoader() {
+        return mySnapshot.getJavaLangClassLoader().isAssignableFrom(this);
+    }
+
+    /**
+     * Get a numbered field from this class
+     */
+    public JavaField getField(int i) {
+        if (i < 0 || i >= fields.length) {
+            throw new Error("No field " + i + " for " + name);
+        }
+        return fields[i];
+    }
+
+    /**
+     * Get the total number of fields that are part of an instance of
+     * this class.  That is, include superclasses.
+     */
+    public int getNumFieldsForInstance() {
+        return totalNumFields;
+    }
+
+    /**
+     * Get a numbered field from all the fields that are part of instance
+     * of this class.  That is, include superclasses.
+     */
+    public JavaField getFieldForInstance(int i) {
+        if (superclass != null) {
+            JavaClass sc = (JavaClass) superclass;
+            if (i < sc.totalNumFields) {
+                return sc.getFieldForInstance(i);
+            }
+            i -= sc.totalNumFields;
+        }
+        return getField(i);
+    }
+
+    /**
+     * Get the class responsible for field i, where i is a field number that
+     * could be passed into getFieldForInstance.
+     *
+     * @see JavaClass.getFieldForInstance()
+     */
+    public JavaClass getClassForField(int i) {
+        if (superclass != null) {
+            JavaClass sc = (JavaClass) superclass;
+            if (i < sc.totalNumFields) {
+                return sc.getClassForField(i);
+            }
+        }
+        return this;
+    }
+
+    public long getId() {
+        return id;
+    }
+
+    public String getName() {
+        return name;
+    }
+
+    public boolean isArray() {
+        return name.indexOf('[') != -1;
+    }
+
+    public Enumeration<JavaHeapObject> getInstances(boolean includeSubclasses) {
+        if (includeSubclasses) {
+            Enumeration<JavaHeapObject> res = instances.elements();
+            for (int i = 0; i < subclasses.length; i++) {
+                res = new CompositeEnumeration(res,
+                              subclasses[i].getInstances(true));
+            }
+            return res;
+        } else {
+            return instances.elements();
+        }
+    }
+
+    /**
+     * @return a count of the instances of this class
+     */
+    public int getInstancesCount(boolean includeSubclasses) {
+        int result = instances.size();
+        if (includeSubclasses) {
+            for (int i = 0; i < subclasses.length; i++) {
+                result += subclasses[i].getInstancesCount(includeSubclasses);
+            }
+        }
+        return result;
+    }
+
+    public JavaClass[] getSubclasses() {
+        return subclasses;
+    }
+
+    /**
+     * This can only safely be called after resolve()
+     */
+    public JavaClass getSuperclass() {
+        return (JavaClass) superclass;
+    }
+
+    /**
+     * This can only safely be called after resolve()
+     */
+    public JavaThing getLoader() {
+        return loader;
+    }
+
+    /**
+     * This can only safely be called after resolve()
+     */
+    public boolean isBootstrap() {
+        return loader == mySnapshot.getNullThing();
+    }
+
+    /**
+     * This can only safely be called after resolve()
+     */
+    public JavaThing getSigners() {
+        return signers;
+    }
+
+    /**
+     * This can only safely be called after resolve()
+     */
+    public JavaThing getProtectionDomain() {
+        return protectionDomain;
+    }
+
+    public JavaField[] getFields() {
+        return fields;
+    }
+
+    /**
+     * Includes superclass fields
+     */
+    public JavaField[] getFieldsForInstance() {
+        Vector<JavaField> v = new Vector<JavaField>();
+        addFields(v);
+        JavaField[] result = new JavaField[v.size()];
+        for (int i = 0; i < v.size(); i++) {
+            result[i] =  v.elementAt(i);
+        }
+        return result;
+    }
+
+
+    public JavaStatic[] getStatics() {
+        return statics;
+    }
+
+    // returns value of static field of given name
+    public JavaThing getStaticField(String name) {
+        for (int i = 0; i < statics.length; i++) {
+            JavaStatic s = statics[i];
+            if (s.getField().getName().equals(name)) {
+                return s.getValue();
+            }
+        }
+        return null;
+    }
+
+    public String toString() {
+        return "class " + name;
+    }
+
+    public int compareTo(JavaThing other) {
+        if (other instanceof JavaClass) {
+            return name.compareTo(((JavaClass) other).name);
+        }
+        return super.compareTo(other);
+    }
+
+
+    /**
+     * @return true iff a variable of type this is assignable from an instance
+     *          of other
+     */
+    public boolean isAssignableFrom(JavaClass other) {
+        if (this == other) {
+            return true;
+        } else if (other == null) {
+            return false;
+        } else {
+            return isAssignableFrom((JavaClass) other.superclass);
+            // Trivial tail recursion:  I have faith in javac.
+        }
+    }
+
+    /**
+     * Describe the reference that this thing has to target.  This will only
+     * be called if target is in the array returned by getChildrenForRootset.
+     */
+     public String describeReferenceTo(JavaThing target, Snapshot ss) {
+        for (int i = 0; i < statics.length; i++) {
+            JavaField f = statics[i].getField();
+            if (f.hasId()) {
+                JavaThing other = statics[i].getValue();
+                if (other == target) {
+                    return "static field " + f.getName();
+                }
+            }
+        }
+        return super.describeReferenceTo(target, ss);
+    }
+
+    /**
+     * @return the size of an instance of this class.  Gives 0 for an array
+     *          type.
+     */
+    public int getInstanceSize() {
+        return instanceSize + mySnapshot.getMinimumObjectSize();
+    }
+
+
+    /**
+     * @return The size of all instances of this class.  Correctly handles
+     *          arrays.
+     */
+    public long getTotalInstanceSize() {
+        int count = instances.size();
+        if (count == 0 || !isArray()) {
+            return count * instanceSize;
+        }
+
+        // array class and non-zero count, we have to
+        // get the size of each instance and sum it
+        long result = 0;
+        for (int i = 0; i < count; i++) {
+            JavaThing t = (JavaThing) instances.elementAt(i);
+            result += t.getSize();
+        }
+        return result;
+    }
+
+    /**
+     * @return the size of this object
+     */
+    public int getSize() {
+        JavaClass cl = mySnapshot.getJavaLangClass();
+        if (cl == null) {
+            return 0;
+        } else {
+            return cl.getInstanceSize();
+        }
+    }
+
+    public void visitReferencedObjects(JavaHeapObjectVisitor v) {
+        super.visitReferencedObjects(v);
+        JavaHeapObject sc = getSuperclass();
+        if (sc != null) v.visit(getSuperclass());
+
+        JavaThing other;
+        other = getLoader();
+        if (other instanceof JavaHeapObject) {
+            v.visit((JavaHeapObject)other);
+        }
+        other = getSigners();
+        if (other instanceof JavaHeapObject) {
+            v.visit((JavaHeapObject)other);
+        }
+        other = getProtectionDomain();
+        if (other instanceof JavaHeapObject) {
+            v.visit((JavaHeapObject)other);
+        }
+
+        for (int i = 0; i < statics.length; i++) {
+            JavaField f = statics[i].getField();
+            if (!v.exclude(this, f) && f.hasId()) {
+                other = statics[i].getValue();
+                if (other instanceof JavaHeapObject) {
+                    v.visit((JavaHeapObject) other);
+                }
+            }
+        }
+    }
+
+    // package-privates below this point
+    final ReadBuffer getReadBuffer() {
+        return mySnapshot.getReadBuffer();
+    }
+
+    final void setNew(JavaHeapObject obj, boolean flag) {
+        mySnapshot.setNew(obj, flag);
+    }
+
+    final boolean isNew(JavaHeapObject obj) {
+        return mySnapshot.isNew(obj);
+    }
+
+    final StackTrace getSiteTrace(JavaHeapObject obj) {
+        return mySnapshot.getSiteTrace(obj);
+    }
+
+    final void addReferenceFromRoot(Root root, JavaHeapObject obj) {
+        mySnapshot.addReferenceFromRoot(root, obj);
+    }
+
+    final Root getRoot(JavaHeapObject obj) {
+        return mySnapshot.getRoot(obj);
+    }
+
+    final Snapshot getSnapshot() {
+        return mySnapshot;
+    }
+
+    void addInstance(JavaHeapObject inst) {
+        instances.addElement(inst);
+    }
+
+    // Internals only below this point
+    private void addFields(Vector<JavaField> v) {
+        if (superclass != null) {
+            ((JavaClass) superclass).addFields(v);
+        }
+        for (int i = 0; i < fields.length; i++) {
+            v.addElement(fields[i]);
+        }
+    }
+
+    private void addSubclassInstances(Vector<JavaHeapObject> v) {
+        for (int i = 0; i < subclasses.length; i++) {
+            subclasses[i].addSubclassInstances(v);
+        }
+        for (int i = 0; i < instances.size(); i++) {
+            v.addElement(instances.elementAt(i));
+        }
+    }
+
+    private void addSubclass(JavaClass sub) {
+        JavaClass newValue[] = new JavaClass[subclasses.length + 1];
+        System.arraycopy(subclasses, 0, newValue, 0, subclasses.length);
+        newValue[subclasses.length] = sub;
+        subclasses = newValue;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/JavaDouble.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,53 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+/**
+ * Represents a double (i.e. a double field in an instance).
+ *
+ * @author      Bill Foote
+ */
+
+
+public class JavaDouble extends JavaValue {
+
+    double value;
+
+    public JavaDouble(double value) {
+        this.value = value;
+    }
+
+    public String toString() {
+        return Double.toString(value);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/JavaField.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,69 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+
+/**
+ *
+ * @author      Bill Foote
+ */
+
+public class JavaField {
+
+    private String name;
+    private String signature;
+
+    public JavaField(String name, String signature) {
+        this.name = name;
+        this.signature = signature;
+    }
+
+
+    /**
+     * @return true if the type of this field is something that has an ID.
+     *          int fields, for exampe, don't.
+     */
+    public boolean hasId() {
+        char ch = signature.charAt(0);
+        return (ch == '[' || ch == 'L');
+    }
+
+    public String getName() {
+        return name;
+    }
+
+    public String getSignature() {
+        return signature;
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/JavaFloat.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,53 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+/**
+ * Represents a float (i.e. a float field in an instance).
+ *
+ * @author      Bill Foote
+ */
+
+
+public class JavaFloat extends JavaValue {
+
+    float value;
+
+    public JavaFloat(float value) {
+        this.value = value;
+    }
+
+    public String toString() {
+        return Float.toString(value);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/JavaHeapObject.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,207 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+import java.util.Enumeration;
+import java.util.HashMap;
+import java.util.Map;
+import jdk.test.lib.hprof.util.Misc;
+
+
+/**
+ *
+ * @author      Bill Foote
+ */
+
+/**
+ * Represents an object that's allocated out of the Java heap.  It occupies
+ * memory in the VM, and is the sort of thing that in a JDK 1.1 VM had
+ * a handle.  It can be a
+ * JavaClass, a JavaObjectArray, a JavaValueArray or a JavaObject.
+ */
+
+public abstract class JavaHeapObject extends JavaThing {
+
+    //
+    // Who we refer to.  This is heavily optimized for space, because it's
+    // well worth trading a bit of speed for less swapping.
+    // referers and referersLen go through two phases:  Building and
+    // resolved.  When building, referers might have duplicates, but can
+    // be appended to.  When resolved, referers has no duplicates or
+    // empty slots.
+    //
+    private JavaThing[] referers = null;
+    private int referersLen = 0;        // -1 when resolved
+
+    public abstract JavaClass getClazz();
+    public abstract int getSize();
+    public abstract long getId();
+
+    /**
+     * Do any initialization this thing needs after its data is read in.
+     * Subclasses that override this should call super.resolve().
+     */
+    public void resolve(Snapshot snapshot) {
+        StackTrace trace = snapshot.getSiteTrace(this);
+        if (trace != null) {
+            trace.resolve(snapshot);
+        }
+    }
+
+    //
+    //  Eliminate duplicates from referers, and size the array exactly.
+    // This sets us up to answer queries.  See the comments around the
+    // referers data member for details.
+    //
+    void setupReferers() {
+        if (referersLen > 1) {
+            // Copy referers to map, screening out duplicates
+            Map<JavaThing, JavaThing> map = new HashMap<JavaThing, JavaThing>();
+            for (int i = 0; i < referersLen; i++) {
+                if (map.get(referers[i]) == null) {
+                    map.put(referers[i], referers[i]);
+                }
+            }
+
+            // Now copy into the array
+            referers = new JavaThing[map.size()];
+            map.keySet().toArray(referers);
+        }
+        referersLen = -1;
+    }
+
+
+    /**
+     * @return the id of this thing as hex string
+     */
+    public String getIdString() {
+        return Misc.toHex(getId());
+    }
+
+    public String toString() {
+        return getClazz().getName() + "@" + getIdString();
+    }
+
+    /**
+     * @return the StackTrace of the point of allocation of this object,
+     *          or null if unknown
+     */
+    public StackTrace getAllocatedFrom() {
+        return getClazz().getSiteTrace(this);
+    }
+
+    public boolean isNew() {
+        return getClazz().isNew(this);
+    }
+
+    void setNew(boolean flag) {
+        getClazz().setNew(this, flag);
+    }
+
+    /**
+     * Tell the visitor about all of the objects we refer to
+     */
+    public void visitReferencedObjects(JavaHeapObjectVisitor v) {
+        v.visit(getClazz());
+    }
+
+    void addReferenceFrom(JavaHeapObject other) {
+        if (referersLen == 0) {
+            referers = new JavaThing[1];        // It was null
+        } else if (referersLen == referers.length) {
+            JavaThing[] copy = new JavaThing[(3 * (referersLen + 1)) / 2];
+            System.arraycopy(referers, 0, copy, 0, referersLen);
+            referers = copy;
+        }
+        referers[referersLen++] = other;
+        // We just append to referers here.  Measurements have shown that
+        // around 10% to 30% are duplicates, so it's better to just append
+        // blindly and screen out all the duplicates at once.
+    }
+
+    void addReferenceFromRoot(Root r) {
+        getClazz().addReferenceFromRoot(r, this);
+    }
+
+    /**
+     * If the rootset includes this object, return a Root describing one
+     * of the reasons why.
+     */
+    public Root getRoot() {
+        return getClazz().getRoot(this);
+    }
+
+    /**
+     * Tell who refers to us.
+     *
+     * @return an Enumeration of JavaHeapObject instances
+     */
+    public Enumeration<JavaThing> getReferers() {
+        if (referersLen != -1) {
+            throw new RuntimeException("not resolved: " + getIdString());
+        }
+        return new Enumeration<JavaThing>() {
+
+            private int num = 0;
+
+            public boolean hasMoreElements() {
+                return referers != null && num < referers.length;
+            }
+
+            public JavaThing nextElement() {
+                return referers[num++];
+            }
+        };
+    }
+
+    /**
+     * Given other, which the caller promises is in referers, determines if
+     * the reference is only a weak reference.
+     */
+    public boolean refersOnlyWeaklyTo(Snapshot ss, JavaThing other) {
+        return false;
+    }
+
+    /**
+     * Describe the reference that this thing has to target.  This will only
+     * be called if target is in the array returned by getChildrenForRootset.
+     */
+    public String describeReferenceTo(JavaThing target, Snapshot ss) {
+        return "??";
+    }
+
+    public boolean isHeapAllocated() {
+        return true;
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/JavaHeapObjectVisitor.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,55 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+/**
+ * A visitor for a JavaThing.  @see JavaObject#visitReferencedObjects()
+ *
+ * @author      Bill Foote
+ */
+
+
+public interface JavaHeapObjectVisitor {
+    public void visit(JavaHeapObject other);
+
+    /**
+     * Should the given field be excluded from the set of things visited?
+     * @return true if it should.
+     */
+    public boolean exclude(JavaClass clazz, JavaField f);
+
+    /**
+     * @return true iff exclude might ever return true
+     */
+    public boolean mightExclude();
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/JavaInt.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,54 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+/**
+ * Represents an integer (i.e. an int field in an instance).
+ *
+ * @author      Bill Foote
+ */
+
+
+public class JavaInt extends JavaValue {
+
+    int value;
+
+    public JavaInt(int value) {
+        this.value = value;
+    }
+
+    public String toString() {
+        return "" + value;
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/JavaLazyReadObject.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,176 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+import java.io.IOException;
+import jdk.test.lib.hprof.parser.ReadBuffer;
+
+/*
+ * Base class for lazily read Java heap objects.
+ */
+public abstract class JavaLazyReadObject extends JavaHeapObject {
+
+    // file offset from which this object data starts
+    private final long offset;
+
+    protected JavaLazyReadObject(long offset) {
+        this.offset = offset;
+    }
+
+    public final int getSize() {
+        return getValueLength() + getClazz().getMinimumObjectSize();
+    }
+
+    protected final long getOffset() {
+        return offset;
+    }
+
+    // return the length of the data for this object
+    protected final int getValueLength() {
+        try {
+            return readValueLength();
+        } catch (IOException exp) {
+            System.err.println("lazy read failed at offset " + offset);
+            exp.printStackTrace();
+            return 0;
+        }
+    }
+
+    // get this object's content as byte array
+    protected final byte[] getValue() {
+        try {
+            return readValue();
+        } catch (IOException exp) {
+            System.err.println("lazy read failed at offset " + offset);
+            exp.printStackTrace();
+            return Snapshot.EMPTY_BYTE_ARRAY;
+        }
+    }
+
+    // get ID of this object
+    public final long getId() {
+        try {
+            ReadBuffer buf = getClazz().getReadBuffer();
+            int idSize = getClazz().getIdentifierSize();
+            if (idSize == 4) {
+                return ((long)buf.getInt(offset)) & Snapshot.SMALL_ID_MASK;
+            } else {
+                return buf.getLong(offset);
+            }
+        } catch (IOException exp) {
+            System.err.println("lazy read failed at offset " + offset);
+            exp.printStackTrace();
+            return -1;
+        }
+    }
+
+    protected abstract int readValueLength() throws IOException;
+    protected abstract byte[] readValue() throws IOException;
+
+    // make Integer or Long for given object ID
+    protected static Number makeId(long id) {
+        if ((id & ~Snapshot.SMALL_ID_MASK) == 0) {
+            return (int)id;
+        } else {
+            return id;
+        }
+    }
+
+    // get ID as long value from Number
+    protected static long getIdValue(Number num) {
+        long id = num.longValue();
+        if (num instanceof Integer) {
+            id &= Snapshot.SMALL_ID_MASK;
+        }
+        return id;
+    }
+
+    // read object ID from given index from given byte array
+    protected final long objectIdAt(int index, byte[] data) {
+        int idSize = getClazz().getIdentifierSize();
+        if (idSize == 4) {
+            return ((long)intAt(index, data)) & Snapshot.SMALL_ID_MASK;
+        } else {
+            return longAt(index, data);
+        }
+    }
+
+    // utility methods to read primitive types from byte array
+    protected static byte byteAt(int index, byte[] value) {
+        return value[index];
+    }
+
+    protected static boolean booleanAt(int index, byte[] value) {
+        return (value[index] & 0xff) == 0? false: true;
+    }
+
+    protected static char charAt(int index, byte[] value) {
+        int b1 = ((int) value[index++] & 0xff);
+        int b2 = ((int) value[index++] & 0xff);
+        return (char) ((b1 << 8) + b2);
+    }
+
+    protected static short shortAt(int index, byte[] value) {
+        int b1 = ((int) value[index++] & 0xff);
+        int b2 = ((int) value[index++] & 0xff);
+        return (short) ((b1 << 8) + b2);
+    }
+
+    protected static int intAt(int index, byte[] value) {
+        int b1 = ((int) value[index++] & 0xff);
+        int b2 = ((int) value[index++] & 0xff);
+        int b3 = ((int) value[index++] & 0xff);
+        int b4 = ((int) value[index++] & 0xff);
+        return ((b1 << 24) + (b2 << 16) + (b3 << 8) + b4);
+    }
+
+    protected static long longAt(int index, byte[] value) {
+        long val = 0;
+        for (int j = 0; j < 8; j++) {
+            val = val << 8;
+            int b = ((int)value[index++]) & 0xff;
+            val |= b;
+        }
+        return val;
+    }
+
+    protected static float floatAt(int index, byte[] value) {
+        int val = intAt(index, value);
+        return Float.intBitsToFloat(val);
+    }
+
+    protected static double doubleAt(int index, byte[] value) {
+        long val = longAt(index, value);
+        return Double.longBitsToDouble(val);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/JavaLong.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,53 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+/**
+ * Represents a long (i.e. a long field in an instance).
+ *
+ * @author      Bill Foote
+ */
+
+
+public class JavaLong extends JavaValue {
+
+    long value;
+
+    public JavaLong(long value) {
+        this.value = value;
+    }
+
+    public String toString() {
+        return Long.toString(value);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/JavaObject.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,334 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+import java.io.IOException;
+import jdk.test.lib.hprof.parser.ReadBuffer;
+
+/**
+ * Represents Java instance
+ *
+ * @author      Bill Foote
+ */
+public class JavaObject extends JavaLazyReadObject {
+
+    private Object clazz;       // Number before resolve
+                                // JavaClass after resolve
+    /**
+     * Construct a new JavaObject.
+     *
+     * @param classID id of the class object
+     * @param offset The offset of field data
+     */
+    public JavaObject(long classID, long offset) {
+        super(offset);
+        this.clazz = makeId(classID);
+    }
+
+    public void resolve(Snapshot snapshot) {
+        if (clazz instanceof JavaClass) {
+            return;
+        }
+        if (clazz instanceof Number) {
+            long classID = getIdValue((Number)clazz);
+            clazz = snapshot.findThing(classID);
+            if (! (clazz instanceof JavaClass)) {
+                warn("Class " + Long.toHexString(classID) + " not found, " +
+                     "adding fake class!");
+                int length;
+                ReadBuffer buf = snapshot.getReadBuffer();
+                int idSize = snapshot.getIdentifierSize();
+                long lenOffset = getOffset() + 2*idSize + 4;
+                try {
+                    length = buf.getInt(lenOffset);
+                } catch (IOException exp) {
+                    throw new RuntimeException(exp);
+                }
+                clazz = snapshot.addFakeInstanceClass(classID, length);
+            }
+        } else {
+            throw new InternalError("should not reach here");
+        }
+
+        JavaClass cl = (JavaClass) clazz;
+        cl.resolve(snapshot);
+
+        // while resolving, parse fields in verbose mode.
+        // but, getFields calls parseFields in non-verbose mode
+        // to avoid printing warnings repeatedly.
+        parseFields(getValue(), true);
+
+        cl.addInstance(this);
+        super.resolve(snapshot);
+    }
+
+    /**
+     * Are we the same type as other?  We are iff our clazz is the
+     * same type as other's.
+     */
+    public boolean isSameTypeAs(JavaThing other) {
+        if (!(other instanceof JavaObject)) {
+            return false;
+        }
+        JavaObject oo = (JavaObject) other;
+        return getClazz().equals(oo.getClazz());
+    }
+
+    /**
+     * Return our JavaClass object.  This may only be called after resolve.
+     */
+    public JavaClass getClazz() {
+        return (JavaClass) clazz;
+    }
+
+    public JavaThing[] getFields() {
+        // pass false to verbose mode so that dereference
+        // warnings are not printed.
+        return parseFields(getValue(), false);
+    }
+
+    // returns the value of field of given name
+    public JavaThing getField(String name) {
+        JavaThing[] flds = getFields();
+        JavaField[] instFields = getClazz().getFieldsForInstance();
+        for (int i = 0; i < instFields.length; i++) {
+            if (instFields[i].getName().equals(name)) {
+                return flds[i];
+            }
+        }
+        return null;
+    }
+
+    public int compareTo(JavaThing other) {
+        if (other instanceof JavaObject) {
+            JavaObject oo = (JavaObject) other;
+            return getClazz().getName().compareTo(oo.getClazz().getName());
+        }
+        return super.compareTo(other);
+    }
+
+    public void visitReferencedObjects(JavaHeapObjectVisitor v) {
+        super.visitReferencedObjects(v);
+        JavaThing[] flds = getFields();
+        for (int i = 0; i < flds.length; i++) {
+            if (flds[i] != null) {
+                if (v.mightExclude()
+                    && v.exclude(getClazz().getClassForField(i),
+                                 getClazz().getFieldForInstance(i)))
+                {
+                    // skip it
+                } else if (flds[i] instanceof JavaHeapObject) {
+                    v.visit((JavaHeapObject) flds[i]);
+                }
+            }
+        }
+    }
+
+    public boolean refersOnlyWeaklyTo(Snapshot ss, JavaThing other) {
+        if (ss.getWeakReferenceClass() != null) {
+            final int referentFieldIndex = ss.getReferentFieldIndex();
+            if (ss.getWeakReferenceClass().isAssignableFrom(getClazz())) {
+                //
+                // REMIND:  This introduces a dependency on the JDK
+                //      implementation that is undesirable.
+                JavaThing[] flds = getFields();
+                for (int i = 0; i < flds.length; i++) {
+                    if (i != referentFieldIndex && flds[i] == other) {
+                        return false;
+                    }
+                }
+                return true;
+            }
+        }
+        return false;
+    }
+
+    /**
+     * Describe the reference that this thing has to target.  This will only
+     * be called if target is in the array returned by getChildrenForRootset.
+     */
+    public String describeReferenceTo(JavaThing target, Snapshot ss) {
+        JavaThing[] flds = getFields();
+        for (int i = 0; i < flds.length; i++) {
+            if (flds[i] == target) {
+                JavaField f = getClazz().getFieldForInstance(i);
+                return "field " + f.getName();
+            }
+        }
+        return super.describeReferenceTo(target, ss);
+    }
+
+    public String toString() {
+        if (getClazz().isString()) {
+            JavaThing value = getField("value");
+            if (value instanceof JavaValueArray) {
+                return ((JavaValueArray)value).valueString();
+            } else {
+                return "null";
+            }
+        } else {
+            return super.toString();
+        }
+    }
+
+    // Internals only below this point
+
+    /*
+     * Java instance record (HPROF_GC_INSTANCE_DUMP) looks as below:
+     *
+     *     object ID
+     *     stack trace serial number (int)
+     *     class ID
+     *     data length (int)
+     *     byte[length]
+     */
+    protected final int readValueLength() throws IOException {
+        JavaClass cl = getClazz();
+        int idSize = cl.getIdentifierSize();
+        long lengthOffset = getOffset() + 2*idSize + 4;
+        return cl.getReadBuffer().getInt(lengthOffset);
+    }
+
+    protected final byte[] readValue() throws IOException {
+        JavaClass cl = getClazz();
+        int idSize = cl.getIdentifierSize();
+        ReadBuffer buf = cl.getReadBuffer();
+        long offset = getOffset() + 2*idSize + 4;
+        int length = buf.getInt(offset);
+        if (length == 0) {
+            return Snapshot.EMPTY_BYTE_ARRAY;
+        } else {
+            byte[] res = new byte[length];
+            buf.get(offset + 4, res);
+            return res;
+        }
+    }
+
+    private JavaThing[] parseFields(byte[] data, boolean verbose) {
+        JavaClass cl = getClazz();
+        int target = cl.getNumFieldsForInstance();
+        JavaField[] fields = cl.getFields();
+        JavaThing[] fieldValues = new JavaThing[target];
+        Snapshot snapshot = cl.getSnapshot();
+        int idSize = snapshot.getIdentifierSize();
+        int fieldNo = 0;
+        // In the dump file, the fields are stored in this order:
+        // fields of most derived class (immediate class) are stored
+        // first and then the super class and so on. In this object,
+        // fields are stored in the reverse ("natural") order. i.e.,
+        // fields of most super class are stored first.
+
+        // target variable is used to compensate for the fact that
+        // the dump file starts field values from the leaf working
+        // upwards in the inheritance hierarchy, whereas JavaObject
+        // starts with the top of the inheritance hierarchy and works down.
+        target -= fields.length;
+        JavaClass currClass = cl;
+        int index = 0;
+        for (int i = 0; i < fieldValues.length; i++, fieldNo++) {
+            while (fieldNo >= fields.length) {
+                currClass = currClass.getSuperclass();
+                fields = currClass.getFields();
+                fieldNo = 0;
+                target -= fields.length;
+            }
+            JavaField f = fields[fieldNo];
+            char sig = f.getSignature().charAt(0);
+            switch (sig) {
+                case 'L':
+                case '[': {
+                    long id = objectIdAt(index, data);
+                    index += idSize;
+                    JavaObjectRef ref = new JavaObjectRef(id);
+                    fieldValues[target+fieldNo] = ref.dereference(snapshot, f, verbose);
+                    break;
+                }
+                case 'Z': {
+                    byte value = byteAt(index, data);
+                    index++;
+                    fieldValues[target+fieldNo] = new JavaBoolean(value != 0);
+                    break;
+                }
+                case 'B': {
+                    byte value = byteAt(index, data);
+                    index++;
+                    fieldValues[target+fieldNo] = new JavaByte(value);
+                    break;
+                }
+                case 'S': {
+                    short value = shortAt(index, data);
+                    index += 2;
+                    fieldValues[target+fieldNo] = new JavaShort(value);
+                    break;
+                }
+                case 'C': {
+                    char value = charAt(index, data);
+                    index += 2;
+                    fieldValues[target+fieldNo] = new JavaChar(value);
+                    break;
+                }
+                case 'I': {
+                    int value = intAt(index, data);
+                    index += 4;
+                    fieldValues[target+fieldNo] = new JavaInt(value);
+                    break;
+                }
+                case 'J': {
+                    long value = longAt(index, data);
+                    index += 8;
+                    fieldValues[target+fieldNo] = new JavaLong(value);
+                    break;
+                }
+                case 'F': {
+                    float value = floatAt(index, data);
+                    index += 4;
+                    fieldValues[target+fieldNo] = new JavaFloat(value);
+                    break;
+                }
+                case 'D': {
+                    double value = doubleAt(index, data);
+                    index += 8;
+                    fieldValues[target+fieldNo] = new JavaDouble(value);
+                    break;
+                }
+                default:
+                    throw new RuntimeException("invalid signature: " + sig);
+            }
+        }
+        return fieldValues;
+    }
+
+    private void warn(String msg) {
+        System.out.println("WARNING: " + msg);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/JavaObjectArray.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,172 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+import java.io.IOException;
+import jdk.test.lib.hprof.parser.ReadBuffer;
+
+/**
+ * @author      Bill Foote
+ */
+public class JavaObjectArray extends JavaLazyReadObject {
+
+    private Object clazz;  // Long before resolve, the class after resolve
+
+    public JavaObjectArray(long classID, long offset) {
+        super(offset);
+        this.clazz = makeId(classID);
+    }
+
+    public JavaClass getClazz() {
+        return (JavaClass) clazz;
+    }
+
+    public void resolve(Snapshot snapshot) {
+        if (clazz instanceof JavaClass) {
+            return;
+        }
+        long classID = getIdValue((Number)clazz);
+        if (snapshot.isNewStyleArrayClass()) {
+            // Modern heap dumps do this
+            JavaThing t = snapshot.findThing(classID);
+            if (t instanceof JavaClass) {
+                clazz = (JavaClass) t;
+            }
+        }
+        if (!(clazz instanceof JavaClass)) {
+            JavaThing t = snapshot.findThing(classID);
+            if (t != null && t instanceof JavaClass) {
+                JavaClass el = (JavaClass) t;
+                String nm = el.getName();
+                if (!nm.startsWith("[")) {
+                    nm = "L" + el.getName() + ";";
+                }
+                clazz = snapshot.getArrayClass(nm);
+            }
+        }
+
+        if (!(clazz instanceof JavaClass)) {
+            clazz = snapshot.getOtherArrayType();
+        }
+        ((JavaClass)clazz).addInstance(this);
+        super.resolve(snapshot);
+    }
+
+    public JavaThing[] getValues() {
+        return getElements();
+    }
+
+    public JavaThing[] getElements() {
+        Snapshot snapshot = getClazz().getSnapshot();
+        byte[] data = getValue();
+        final int idSize = snapshot.getIdentifierSize();
+        final int numElements = data.length / idSize;
+        JavaThing[] elements = new JavaThing[numElements];
+        int index = 0;
+        for (int i = 0; i < elements.length; i++) {
+            long id = objectIdAt(index, data);
+            index += idSize;
+            elements[i] = snapshot.findThing(id);
+        }
+        return elements;
+    }
+
+    public int compareTo(JavaThing other) {
+        if (other instanceof JavaObjectArray) {
+            return 0;
+        }
+        return super.compareTo(other);
+    }
+
+    public int getLength() {
+        return getValueLength() / getClazz().getIdentifierSize();
+    }
+
+    public void visitReferencedObjects(JavaHeapObjectVisitor v) {
+        super.visitReferencedObjects(v);
+        JavaThing[] elements = getElements();
+        for (int i = 0; i < elements.length; i++) {
+            if (elements[i] != null && elements[i] instanceof JavaHeapObject) {
+                v.visit((JavaHeapObject) elements[i]);
+            }
+        }
+    }
+
+    /**
+     * Describe the reference that this thing has to target.  This will only
+     * be called if target is in the array returned by getChildrenForRootset.
+     */
+    public String describeReferenceTo(JavaThing target, Snapshot ss) {
+        JavaThing[] elements = getElements();
+        for (int i = 0; i < elements.length; i++) {
+            if (elements[i] == target) {
+                return "Element " + i + " of " + this;
+            }
+        }
+        return super.describeReferenceTo(target, ss);
+    }
+
+    /*
+     * Java object array record (HPROF_GC_OBJ_ARRAY_DUMP)
+     * looks as below:
+     *
+     *     object ID
+     *     stack trace serial number (int)
+     *     array length (int)
+     *     array class ID
+     *     array element IDs
+     */
+    protected final int readValueLength() throws IOException {
+        JavaClass cl = getClazz();
+        ReadBuffer buf = cl.getReadBuffer();
+        int idSize = cl.getIdentifierSize();
+        long offset = getOffset() + idSize + 4;
+        int len = buf.getInt(offset);
+        return len * cl.getIdentifierSize();
+    }
+
+    protected final byte[] readValue() throws IOException {
+        JavaClass cl = getClazz();
+        ReadBuffer buf = cl.getReadBuffer();
+        int idSize = cl.getIdentifierSize();
+        long offset = getOffset() + idSize + 4;
+        int len = buf.getInt(offset);
+        if (len == 0) {
+            return Snapshot.EMPTY_BYTE_ARRAY;
+        } else {
+            byte[] res = new byte[len * idSize];
+            buf.get(offset + 4 + idSize, res);
+            return res;
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/JavaObjectRef.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,97 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+import jdk.test.lib.hprof.util.Misc;
+
+/**
+ * A forward reference to an object.  This is an intermediate representation
+ * for a JavaThing, when we have the thing's ID, but we might not have read
+ * the thing yet.
+ *
+ * @author      Bill Foote
+ */
+public class JavaObjectRef extends JavaThing {
+    private long id;
+
+    public JavaObjectRef(long id) {
+        this.id = id;
+    }
+
+    public long getId() {
+        return id;
+    }
+
+    public boolean isHeapAllocated() {
+        return true;
+    }
+
+    public JavaThing dereference(Snapshot snapshot, JavaField field) {
+        return dereference(snapshot, field, true);
+    }
+
+    public JavaThing dereference(Snapshot snapshot, JavaField field, boolean verbose) {
+        if (field != null && !field.hasId()) {
+            // If this happens, we must be a field that represents an int.
+            // (This only happens with .bod-style files)
+            return new JavaLong(id);
+        }
+        if (id == 0) {
+            return snapshot.getNullThing();
+        }
+        JavaThing result = snapshot.findThing(id);
+        if (result == null) {
+            if (!snapshot.getUnresolvedObjectsOK() && verbose) {
+                String msg = "WARNING:  Failed to resolve object id "
+                                + Misc.toHex(id);
+                if (field != null) {
+                    msg += " for field " + field.getName()
+                            + " (signature " + field.getSignature() + ")";
+                }
+                System.out.println(msg);
+                // Thread.dumpStack();
+            }
+            result = new HackJavaValue("Unresolved object "
+                                        + Misc.toHex(id), 0);
+        }
+        return result;
+    }
+
+    public int getSize() {
+        return 0;
+    }
+
+    public String toString() {
+        return "Unresolved object " + Misc.toHex(id);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/JavaShort.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,54 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+/**
+ * Represents a short (i.e. a short field in an instance).
+ *
+ * @author      Bill Foote
+ */
+
+
+public class JavaShort extends JavaValue {
+
+    short value;
+
+    public JavaShort(short value) {
+        this.value = value;
+    }
+
+    public String toString() {
+        return "" + value;
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/JavaStatic.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,79 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+/**
+ *
+ * @author      Bill Foote
+ */
+
+/**
+ * Represents the value of a static field of a JavaClass
+ */
+
+public class JavaStatic {
+
+    private JavaField field;
+    private JavaThing value;
+
+    public JavaStatic(JavaField field, JavaThing value) {
+        this.field = field;
+        this.value = value;
+    }
+
+    public void resolve(JavaClass clazz, Snapshot snapshot) {
+        long id = -1;
+        if (value instanceof JavaObjectRef) {
+            id = ((JavaObjectRef)value).getId();
+        }
+        value = value.dereference(snapshot, field);
+        if (value.isHeapAllocated() &&
+            clazz.getLoader() == snapshot.getNullThing()) {
+            // static fields are only roots if they are in classes
+            //    loaded by the root classloader.
+            JavaHeapObject ho = (JavaHeapObject) value;
+            String s = "Static reference from " + clazz.getName()
+                       + "." + field.getName();
+            snapshot.addRoot(new Root(id, clazz.getId(),
+                                      Root.JAVA_STATIC, s));
+        }
+    }
+
+    public JavaField getField() {
+        return field;
+    }
+
+    public JavaThing getValue() {
+        return value;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/JavaThing.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,99 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+import java.util.Enumeration;
+import java.util.Hashtable;
+
+
+/**
+ *
+ * @author      Bill Foote
+ */
+
+
+/**
+ * Represents a java "Thing".  A thing is anything that can be the value of
+ * a field.  This includes JavaHeapObject, JavaObjectRef, and JavaValue.
+ */
+
+public abstract class JavaThing {
+
+    protected JavaThing() {
+    }
+
+    /**
+     * If this is a forward reference, figure out what it really
+     * refers to.
+     *
+     * @param snapshot  The snapshot this is for
+     * @param field     The field this thing represents.  If null, it is
+     *                  assumed this thing is an object (and never a value).
+     */
+    public JavaThing dereference(Snapshot shapshot, JavaField field) {
+        return this;
+    }
+
+
+    /**
+     * Are we the same type as other?
+     *
+     * @see JavaObject.isSameTypeAs()
+     */
+    public boolean isSameTypeAs(JavaThing other) {
+        return getClass() == other.getClass();
+    }
+    /**
+     * @return true iff this represents a heap-allocated object
+     */
+    abstract public boolean isHeapAllocated();
+
+    /**
+     * @return the size of this object, in bytes, including VM overhead
+     */
+    abstract public int getSize();
+
+    /**
+     * @return a human-readable string representation of this thing
+     */
+    abstract public String toString();
+
+    /**
+     * Compare our string representation to other's
+     * @see java.lang.String.compareTo()
+     */
+    public int compareTo(JavaThing other) {
+        return toString().compareTo(other.toString());
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/JavaValue.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,61 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+/**
+ * Abstract base class for all value types (ints, longs, floats, etc.)
+ *
+ * @author      Bill Foote
+ */
+
+
+
+
+public abstract class JavaValue extends JavaThing {
+
+    protected JavaValue() {
+    }
+
+    public boolean isHeapAllocated() {
+        return false;
+    }
+
+    abstract public String toString();
+
+    public int getSize() {
+        // The size of a value is already accounted for in the class
+        // that has the data member.
+        return 0;
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/JavaValueArray.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,433 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+import jdk.test.lib.hprof.parser.ReadBuffer;
+import java.io.IOException;
+
+/**
+ * An array of values, that is, an array of ints, boolean, floats or the like.
+ *
+ * @author      Bill Foote
+ */
+public class JavaValueArray extends JavaLazyReadObject
+                /*imports*/ implements ArrayTypeCodes {
+
+    private static String arrayTypeName(byte sig) {
+        switch (sig) {
+            case 'B':
+                return "byte[]";
+            case 'Z':
+                return "boolean[]";
+            case 'C':
+                return "char[]";
+            case 'S':
+                return "short[]";
+            case 'I':
+                return "int[]";
+            case 'F':
+                return "float[]";
+            case 'J':
+                return "long[]";
+            case 'D':
+                return "double[]";
+            default:
+                throw new RuntimeException("invalid array element sig: " + sig);
+        }
+    }
+
+    private static int elementSize(byte type) {
+        switch (type) {
+            case T_BYTE:
+            case T_BOOLEAN:
+                return 1;
+            case T_CHAR:
+            case T_SHORT:
+                return 2;
+            case T_INT:
+            case T_FLOAT:
+                return 4;
+            case T_LONG:
+            case T_DOUBLE:
+                return 8;
+            default:
+                throw new RuntimeException("invalid array element type: " + type);
+        }
+    }
+
+    /*
+     * Java primitive array record (HPROF_GC_PRIM_ARRAY_DUMP) looks
+     * as below:
+     *
+     *    object ID
+     *    stack trace serial number (int)
+     *    length of the instance data (int)
+     *    element type (byte)
+     *    array data
+     */
+    protected final int readValueLength() throws IOException {
+        JavaClass cl = getClazz();
+        ReadBuffer buf = cl.getReadBuffer();
+        int idSize = cl.getIdentifierSize();
+        long offset = getOffset() + idSize + 4;
+        // length of the array
+        int len = buf.getInt(offset);
+        // typecode of array element type
+        byte type = buf.getByte(offset + 4);
+        return len * elementSize(type);
+    }
+
+    protected final byte[] readValue() throws IOException {
+        JavaClass cl = getClazz();
+        ReadBuffer buf = cl.getReadBuffer();
+        int idSize = cl.getIdentifierSize();
+        long offset = getOffset() + idSize + 4;
+        // length of the array
+        int length = buf.getInt(offset);
+        // typecode of array element type
+        byte type = buf.getByte(offset + 4);
+        if (length == 0) {
+            return Snapshot.EMPTY_BYTE_ARRAY;
+        } else {
+            length *= elementSize(type);
+            byte[] res = new byte[length];
+            buf.get(offset + 5, res);
+            return res;
+        }
+    }
+
+    // JavaClass set only after resolve.
+    private JavaClass clazz;
+
+    // This field contains elementSignature byte and
+    // divider to be used to calculate length. Note that
+    // length of content byte[] is not same as array length.
+    // Actual array length is (byte[].length / divider)
+    private int data;
+
+    // First 8 bits of data is used for element signature
+    private static final int SIGNATURE_MASK = 0x0FF;
+
+    // Next 8 bits of data is used for length divider
+    private static final int LENGTH_DIVIDER_MASK = 0x0FF00;
+
+    // Number of bits to shift to get length divider
+    private static final int LENGTH_DIVIDER_SHIFT = 8;
+
+    public JavaValueArray(byte elementSignature, long offset) {
+        super(offset);
+        this.data = (elementSignature & SIGNATURE_MASK);
+    }
+
+    public JavaClass getClazz() {
+        return clazz;
+    }
+
+    public void visitReferencedObjects(JavaHeapObjectVisitor v) {
+        super.visitReferencedObjects(v);
+    }
+
+    public void resolve(Snapshot snapshot) {
+        if (clazz instanceof JavaClass) {
+            return;
+        }
+        byte elementSig = getElementType();
+        clazz = snapshot.findClass(arrayTypeName(elementSig));
+        if (clazz == null) {
+            clazz = snapshot.getArrayClass("" + ((char) elementSig));
+        }
+        getClazz().addInstance(this);
+        super.resolve(snapshot);
+    }
+
+    public int getLength() {
+        int divider = (data & LENGTH_DIVIDER_MASK) >>> LENGTH_DIVIDER_SHIFT;
+        if (divider == 0) {
+            byte elementSignature = getElementType();
+            switch (elementSignature) {
+            case 'B':
+            case 'Z':
+                divider = 1;
+                break;
+            case 'C':
+            case 'S':
+                divider = 2;
+                break;
+            case 'I':
+            case 'F':
+                divider = 4;
+                break;
+            case 'J':
+            case 'D':
+                divider = 8;
+                break;
+            default:
+                throw new RuntimeException("unknown primitive type: " +
+                                elementSignature);
+            }
+            data |= (divider << LENGTH_DIVIDER_SHIFT);
+        }
+        return (getValueLength() / divider);
+    }
+
+    public Object getElements() {
+        final int len = getLength();
+        final byte et = getElementType();
+        byte[] data = getValue();
+        int index = 0;
+        switch (et) {
+            case 'Z': {
+                boolean[] res = new boolean[len];
+                for (int i = 0; i < len; i++) {
+                    res[i] = booleanAt(index, data);
+                    index++;
+                }
+                return res;
+            }
+            case 'B': {
+                byte[] res = new byte[len];
+                for (int i = 0; i < len; i++) {
+                    res[i] = byteAt(index, data);
+                    index++;
+                }
+                return res;
+            }
+            case 'C': {
+                char[] res = new char[len];
+                for (int i = 0; i < len; i++) {
+                    res[i] = charAt(index, data);
+                    index += 2;
+                }
+                return res;
+            }
+            case 'S': {
+                short[] res = new short[len];
+                for (int i = 0; i < len; i++) {
+                    res[i] = shortAt(index, data);
+                    index += 2;
+                }
+                return res;
+            }
+            case 'I': {
+                int[] res = new int[len];
+                for (int i = 0; i < len; i++) {
+                    res[i] = intAt(index, data);
+                    index += 4;
+                }
+                return res;
+            }
+            case 'J': {
+                long[] res = new long[len];
+                for (int i = 0; i < len; i++) {
+                    res[i] = longAt(index, data);
+                    index += 8;
+                }
+                return res;
+            }
+            case 'F': {
+                float[] res = new float[len];
+                for (int i = 0; i < len; i++) {
+                    res[i] = floatAt(index, data);
+                    index += 4;
+                }
+                return res;
+            }
+            case 'D': {
+                double[] res = new double[len];
+                for (int i = 0; i < len; i++) {
+                    res[i] = doubleAt(index, data);
+                    index += 8;
+                }
+                return res;
+            }
+            default: {
+                throw new RuntimeException("unknown primitive type?");
+            }
+        }
+    }
+
+    public byte getElementType() {
+        return (byte) (data & SIGNATURE_MASK);
+    }
+
+    private void checkIndex(int index) {
+        if (index < 0 || index >= getLength()) {
+            throw new ArrayIndexOutOfBoundsException(index);
+        }
+    }
+
+    private void requireType(char type) {
+        if (getElementType() != type) {
+            throw new RuntimeException("not of type : " + type);
+        }
+    }
+
+    public boolean getBooleanAt(int index) {
+        checkIndex(index);
+        requireType('Z');
+        return booleanAt(index, getValue());
+    }
+
+    public byte getByteAt(int index) {
+        checkIndex(index);
+        requireType('B');
+        return byteAt(index, getValue());
+    }
+
+    public char getCharAt(int index) {
+        checkIndex(index);
+        requireType('C');
+        return charAt(index << 1, getValue());
+    }
+
+    public short getShortAt(int index) {
+        checkIndex(index);
+        requireType('S');
+        return shortAt(index << 1, getValue());
+    }
+
+    public int getIntAt(int index) {
+        checkIndex(index);
+        requireType('I');
+        return intAt(index << 2, getValue());
+    }
+
+    public long getLongAt(int index) {
+        checkIndex(index);
+        requireType('J');
+        return longAt(index << 3, getValue());
+    }
+
+    public float getFloatAt(int index) {
+        checkIndex(index);
+        requireType('F');
+        return floatAt(index << 2, getValue());
+    }
+
+    public double getDoubleAt(int index) {
+        checkIndex(index);
+        requireType('D');
+        return doubleAt(index << 3, getValue());
+    }
+
+    public String valueString() {
+        return valueString(true);
+    }
+
+    public String valueString(boolean bigLimit) {
+        // Char arrays deserve special treatment
+        StringBuilder result;
+        byte[] value = getValue();
+        int max = value.length;
+        byte elementSignature = getElementType();
+        if (elementSignature == 'C')  {
+            result = new StringBuilder();
+            for (int i = 0; i < value.length; ) {
+                char val = charAt(i, value);
+                result.append(val);
+                i += 2;
+            }
+        } else {
+            int limit = 8;
+            if (bigLimit) {
+                limit = 1000;
+            }
+            result = new StringBuilder("{");
+            int num = 0;
+            for (int i = 0; i < value.length; ) {
+                if (num > 0) {
+                    result.append(", ");
+                }
+                if (num >= limit) {
+                    result.append("... ");
+                    break;
+                }
+                num++;
+                switch (elementSignature) {
+                    case 'Z': {
+                        boolean val = booleanAt(i, value);
+                        if (val) {
+                            result.append("true");
+                        } else {
+                            result.append("false");
+                        }
+                        i++;
+                        break;
+                    }
+                    case 'B': {
+                        int val = 0xFF & byteAt(i, value);
+                        result.append("0x").append(Integer.toString(val, 16));
+                        i++;
+                        break;
+                    }
+                    case 'S': {
+                        short val = shortAt(i, value);
+                        i += 2;
+                        result.append(val);
+                        break;
+                    }
+                    case 'I': {
+                        int val = intAt(i, value);
+                        i += 4;
+                        result.append(val);
+                        break;
+                    }
+                    case 'J': {         // long
+                        long val = longAt(i, value);
+                        result.append(val);
+                        i += 8;
+                        break;
+                    }
+                    case 'F': {
+                        float val = floatAt(i, value);
+                        result.append(val);
+                        i += 4;
+                        break;
+                    }
+                    case 'D': {         // double
+                        double val = doubleAt(i, value);
+                        result.append(val);
+                        i += 8;
+                        break;
+                    }
+                    default: {
+                        throw new RuntimeException("unknown primitive type?");
+                    }
+                }
+            }
+            result.append('}');
+        }
+        return result.toString();
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/ReachableExcludes.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,50 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+
+/**
+ * This represents a set of data members that should be excluded from the
+ * reachable objects query. This is useful to exclude observers from the
+ * transitive closure of objects reachable from a given object, allowing
+ * some kind of real determination of the "size" of that object.
+ *
+ */
+
+public interface ReachableExcludes {
+    /**
+     * @return true iff the given field is on the hitlist of excluded
+     *          fields.
+     */
+    public boolean isExcluded(String fieldName);
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/ReachableExcludesImpl.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,103 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.InputStreamReader;
+import java.io.Reader;
+import java.io.BufferedReader;
+import java.io.IOException;
+
+import java.util.Hashtable;
+
+/**
+ * This represents a set of data members that should be excluded from the
+ * reachable objects query.
+ * This is useful to exclude observers from the
+ * transitive closure of objects reachable from a given object, allowing
+ * some kind of real determination of the "size" of that object.
+ *
+ * @author      Bill Foote
+ */
+public class ReachableExcludesImpl implements ReachableExcludes {
+
+    private File excludesFile;
+    private long lastModified;
+    private Hashtable<String, String> methods;  // Used as a bag
+
+    /**
+     * Create a new ReachableExcludesImpl over the given file.  The file will be
+     * re-read whenever the timestamp changes.
+     */
+    public ReachableExcludesImpl(File excludesFile) {
+        this.excludesFile = excludesFile;
+        readFile();
+    }
+
+    private void readFileIfNeeded() {
+        if (excludesFile.lastModified() != lastModified) {
+            synchronized(this) {
+                if (excludesFile.lastModified() != lastModified) {
+                    readFile();
+                }
+            }
+        }
+    }
+
+    private void readFile() {
+        long lm = excludesFile.lastModified();
+        Hashtable<String, String> m = new Hashtable<String, String>();
+
+        try (BufferedReader r = new BufferedReader(new InputStreamReader(
+                new FileInputStream(excludesFile)))) {
+            String method;
+            while ((method = r.readLine()) != null) {
+                m.put(method, method);
+            }
+            lastModified = lm;
+            methods = m;        // We want this to be atomic
+        } catch (IOException ex) {
+            System.out.println("Error reading " + excludesFile + ":  " + ex);
+        }
+    }
+
+    /**
+     * @return true iff the given field is on the histlist of excluded
+     *          fields.
+     */
+    public boolean isExcluded(String fieldName) {
+        readFileIfNeeded();
+        return methods.get(fieldName) != null;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/ReachableObjects.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,148 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+import java.util.Vector;
+import java.util.Hashtable;
+import java.util.Enumeration;
+
+import jdk.test.lib.hprof.util.ArraySorter;
+import jdk.test.lib.hprof.util.Comparer;
+
+/**
+ * @author      A. Sundararajan
+ */
+
+public class ReachableObjects {
+    public ReachableObjects(JavaHeapObject root,
+                            final ReachableExcludes excludes) {
+        this.root = root;
+
+        final Hashtable<JavaHeapObject, JavaHeapObject> bag = new Hashtable<JavaHeapObject, JavaHeapObject>();
+        final Hashtable<String, String> fieldsExcluded = new Hashtable<String, String>();  //Bag<String>
+        final Hashtable<String, String> fieldsUsed = new Hashtable<String, String>();   // Bag<String>
+        JavaHeapObjectVisitor visitor = new AbstractJavaHeapObjectVisitor() {
+            public void visit(JavaHeapObject t) {
+                // Size is zero for things like integer fields
+                if (t != null && t.getSize() > 0 && bag.get(t) == null) {
+                    bag.put(t, t);
+                    t.visitReferencedObjects(this);
+                }
+            }
+
+            public boolean mightExclude() {
+                return excludes != null;
+            }
+
+            public boolean exclude(JavaClass clazz, JavaField f) {
+                if (excludes == null) {
+                    return false;
+                }
+                String nm = clazz.getName() + "." + f.getName();
+                if (excludes.isExcluded(nm)) {
+                    fieldsExcluded.put(nm, nm);
+                    return true;
+                } else {
+                    fieldsUsed.put(nm, nm);
+                    return false;
+                }
+            }
+        };
+        // Put the closure of root and all objects reachable from root into
+        // bag (depth first), but don't include root:
+        visitor.visit(root);
+        bag.remove(root);
+
+        // Now grab the elements into a vector, and sort it in decreasing size
+        JavaThing[] things = new JavaThing[bag.size()];
+        int i = 0;
+        for (Enumeration<JavaHeapObject> e = bag.elements(); e.hasMoreElements(); ) {
+            things[i++] = (JavaThing) e.nextElement();
+        }
+        ArraySorter.sort(things, new Comparer() {
+            public int compare(Object lhs, Object rhs) {
+                JavaThing left = (JavaThing) lhs;
+                JavaThing right = (JavaThing) rhs;
+                int diff = right.getSize() - left.getSize();
+                if (diff != 0) {
+                    return diff;
+                }
+                return left.compareTo(right);
+            }
+        });
+        this.reachables = things;
+
+        this.totalSize = root.getSize();
+        for (i = 0; i < things.length; i++) {
+            this.totalSize += things[i].getSize();
+        }
+
+        excludedFields = getElements(fieldsExcluded);
+        usedFields = getElements(fieldsUsed);
+    }
+
+    public JavaHeapObject getRoot() {
+        return root;
+    }
+
+    public JavaThing[] getReachables() {
+        return reachables;
+    }
+
+    public long getTotalSize() {
+        return totalSize;
+    }
+
+    public String[] getExcludedFields() {
+        return excludedFields;
+    }
+
+    public String[] getUsedFields() {
+        return usedFields;
+    }
+
+    private String[] getElements(Hashtable<?, ?> ht) {
+        Object[] keys = ht.keySet().toArray();
+        int len = keys.length;
+        String[] res = new String[len];
+        System.arraycopy(keys, 0, res, 0, len);
+        ArraySorter.sortArrayOfStrings(res);
+        return res;
+    }
+
+    private JavaHeapObject root;
+    private JavaThing[] reachables;
+    private String[]  excludedFields;
+    private String[]  usedFields;
+    private long totalSize;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/ReferenceChain.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,69 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+/**
+ * Represents a chain of references to some target object
+ *
+ * @author      Bill Foote
+ */
+
+public class ReferenceChain {
+
+    JavaHeapObject      obj;    // Object referred to
+    ReferenceChain      next;   // Next in chain
+
+    public ReferenceChain(JavaHeapObject obj, ReferenceChain next) {
+        this.obj = obj;
+        this.next = next;
+    }
+
+    public JavaHeapObject getObj() {
+        return obj;
+    }
+
+    public ReferenceChain getNext() {
+        return next;
+    }
+
+    public int getDepth() {
+        int count = 1;
+        ReferenceChain tmp = next;
+        while (tmp != null) {
+            count++;
+            tmp = tmp.next;
+        }
+        return count;
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/Root.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,174 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+import jdk.test.lib.hprof.util.Misc;
+
+/**
+ *
+ * @author      Bill Foote
+ */
+
+
+/**
+ * Represents a member of the rootset, that is, one of the objects that
+ * the GC starts from when marking reachable objects.
+ */
+
+public class Root {
+
+    private long id;            // ID of the JavaThing we refer to
+    private long refererId;     // Thread or Class responsible for this, or 0
+    private int index = -1;             // Index in Snapshot.roots
+    private int type;
+    private String description;
+    private JavaHeapObject referer = null;
+    private StackTrace stackTrace = null;
+
+    // Values for type.  Higher values are more interesting -- see getType().
+    // See also getTypeName()
+    public final static int INVALID_TYPE = 0;
+    public final static int UNKNOWN = 1;
+    public final static int SYSTEM_CLASS = 2;
+
+    public final static int NATIVE_LOCAL = 3;
+    public final static int NATIVE_STATIC = 4;
+    public final static int THREAD_BLOCK = 5;
+    public final static int BUSY_MONITOR = 6;
+    public final static int JAVA_LOCAL = 7;
+    public final static int NATIVE_STACK = 8;
+    public final static int JAVA_STATIC = 9;
+
+
+    public Root(long id, long refererId, int type, String description) {
+        this(id, refererId, type, description, null);
+    }
+
+
+    public Root(long id, long refererId, int type, String description,
+                StackTrace stackTrace) {
+        this.id = id;
+        this.refererId = refererId;
+        this.type = type;
+        this.description = description;
+        this.stackTrace = stackTrace;
+    }
+
+    public long getId() {
+        return id;
+    }
+
+    public String getIdString() {
+        return Misc.toHex(id);
+    }
+
+    public String getDescription() {
+        if ("".equals(description)) {
+            return getTypeName() + " Reference";
+        } else {
+            return description;
+        }
+    }
+
+    /**
+     * Return type.  We guarantee that more interesting roots will have
+     * a type that is numerically higher.
+     */
+    public int getType() {
+        return type;
+    }
+
+    public String getTypeName() {
+        switch(type) {
+            case INVALID_TYPE:          return "Invalid (?!?)";
+            case UNKNOWN:               return "Unknown";
+            case SYSTEM_CLASS:          return "System Class";
+            case NATIVE_LOCAL:          return "JNI Local";
+            case NATIVE_STATIC:         return "JNI Global";
+            case THREAD_BLOCK:          return "Thread Block";
+            case BUSY_MONITOR:          return "Busy Monitor";
+            case JAVA_LOCAL:            return "Java Local";
+            case NATIVE_STACK:          return "Native Stack (possibly Java local)";
+            case JAVA_STATIC:           return "Java Static";
+            default:                    return "??";
+        }
+    }
+
+    /**
+     * Given two Root instances, return the one that is most interesting.
+     */
+    public Root mostInteresting(Root other) {
+        if (other.type > this.type) {
+            return other;
+        } else {
+            return this;
+        }
+    }
+
+    /**
+     * Get the object that's responsible for this root, if there is one.
+     * This will be null, a Thread object, or a Class object.
+     */
+    public JavaHeapObject getReferer() {
+        return referer;
+    }
+
+    /**
+     * @return the stack trace responsible for this root, or null if there
+     * is none.
+     */
+    public StackTrace getStackTrace() {
+        return stackTrace;
+    }
+
+    /**
+     * @return The index of this root in Snapshot.roots
+     */
+    public int getIndex() {
+        return index;
+    }
+
+    void resolve(Snapshot ss) {
+        if (refererId != 0) {
+            referer = ss.findThing(refererId);
+        }
+        if (stackTrace != null) {
+            stackTrace.resolve(ss);
+        }
+    }
+
+    void setIndex(int i) {
+        index = i;
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/Snapshot.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,637 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+import java.lang.ref.SoftReference;
+import java.util.*;
+
+import jdk.test.lib.hprof.parser.ReadBuffer;
+import jdk.test.lib.hprof.util.Misc;
+
+/**
+ *
+ * @author      Bill Foote
+ */
+
+/**
+ * Represents a snapshot of the Java objects in the VM at one instant.
+ * This is the top-level "model" object read out of a single .hprof or .bod
+ * file.
+ */
+
+public class Snapshot implements AutoCloseable {
+
+    public static final long SMALL_ID_MASK = 0x0FFFFFFFFL;
+    public static final byte[] EMPTY_BYTE_ARRAY = new byte[0];
+
+    private static final JavaField[] EMPTY_FIELD_ARRAY = new JavaField[0];
+    private static final JavaStatic[] EMPTY_STATIC_ARRAY = new JavaStatic[0];
+
+    // all heap objects
+    private Hashtable<Number, JavaHeapObject> heapObjects =
+                 new Hashtable<Number, JavaHeapObject>();
+
+    private Hashtable<Number, JavaClass> fakeClasses =
+                 new Hashtable<Number, JavaClass>();
+
+    // all Roots in this Snapshot
+    private Vector<Root> roots = new Vector<Root>();
+
+    // name-to-class map
+    private Map<String, JavaClass> classes =
+                 new TreeMap<String, JavaClass>();
+
+    // new objects relative to a baseline - lazily initialized
+    private volatile Map<JavaHeapObject, Boolean> newObjects;
+
+    // allocation site traces for all objects - lazily initialized
+    private volatile Map<JavaHeapObject, StackTrace> siteTraces;
+
+    // object-to-Root map for all objects
+    private Map<JavaHeapObject, Root> rootsMap =
+                 new HashMap<JavaHeapObject, Root>();
+
+    // soft cache of finalizeable objects - lazily initialized
+    private SoftReference<Vector<?>> finalizablesCache;
+
+    // represents null reference
+    private JavaThing nullThing;
+
+    // java.lang.ref.Reference class
+    private JavaClass weakReferenceClass;
+    // index of 'referent' field in java.lang.ref.Reference class
+    private int referentFieldIndex;
+
+    // java.lang.Class class
+    private JavaClass javaLangClass;
+    // java.lang.String class
+    private JavaClass javaLangString;
+    // java.lang.ClassLoader class
+    private JavaClass javaLangClassLoader;
+
+    // unknown "other" array class
+    private volatile JavaClass otherArrayType;
+    // Stuff to exclude from reachable query
+    private ReachableExcludes reachableExcludes;
+    // the underlying heap dump buffer
+    private ReadBuffer readBuf;
+
+    // True iff some heap objects have isNew set
+    private boolean hasNewSet;
+    private boolean unresolvedObjectsOK;
+
+    // whether object array instances have new style class or
+    // old style (element) class.
+    private boolean newStyleArrayClass;
+
+    // object id size in the heap dump
+    private int identifierSize = 4;
+
+    // minimum object size - accounts for object header in
+    // most Java virtual machines - we assume 2 identifierSize
+    // (which is true for Sun's hotspot JVM).
+    private int minimumObjectSize;
+
+    public Snapshot(ReadBuffer buf) {
+        nullThing = new HackJavaValue("<null>", 0);
+        readBuf = buf;
+    }
+
+    public void setSiteTrace(JavaHeapObject obj, StackTrace trace) {
+        if (trace != null && trace.getFrames().length != 0) {
+            initSiteTraces();
+            siteTraces.put(obj, trace);
+        }
+    }
+
+    public StackTrace getSiteTrace(JavaHeapObject obj) {
+        if (siteTraces != null) {
+            return siteTraces.get(obj);
+        } else {
+            return null;
+        }
+    }
+
+    public void setNewStyleArrayClass(boolean value) {
+        newStyleArrayClass = value;
+    }
+
+    public boolean isNewStyleArrayClass() {
+        return newStyleArrayClass;
+    }
+
+    public void setIdentifierSize(int size) {
+        identifierSize = size;
+        minimumObjectSize = 2 * size;
+    }
+
+    public int getIdentifierSize() {
+        return identifierSize;
+    }
+
+    public int getMinimumObjectSize() {
+        return minimumObjectSize;
+    }
+
+    public void addHeapObject(long id, JavaHeapObject ho) {
+        heapObjects.put(makeId(id), ho);
+    }
+
+    public void addRoot(Root r) {
+        r.setIndex(roots.size());
+        roots.addElement(r);
+    }
+
+    public void addClass(long id, JavaClass c) {
+        addHeapObject(id, c);
+        putInClassesMap(c);
+    }
+
+    JavaClass addFakeInstanceClass(long classID, int instSize) {
+        // Create a fake class name based on ID.
+        String name = "unknown-class<@" + Misc.toHex(classID) + ">";
+
+        // Create fake fields convering the given instance size.
+        // Create as many as int type fields and for the left over
+        // size create byte type fields.
+        int numInts = instSize / 4;
+        int numBytes = instSize % 4;
+        JavaField[] fields = new JavaField[numInts + numBytes];
+        int i;
+        for (i = 0; i < numInts; i++) {
+            fields[i] = new JavaField("unknown-field-" + i, "I");
+        }
+        for (i = 0; i < numBytes; i++) {
+            fields[i + numInts] = new JavaField("unknown-field-" +
+                                                i + numInts, "B");
+        }
+
+        // Create fake instance class
+        JavaClass c = new JavaClass(name, 0, 0, 0, 0, fields,
+                                 EMPTY_STATIC_ARRAY, instSize);
+        // Add the class
+        addFakeClass(makeId(classID), c);
+        return c;
+    }
+
+
+    /**
+     * @return true iff it's possible that some JavaThing instances might
+     *          isNew set
+     *
+     * @see JavaThing.isNew()
+     */
+    public boolean getHasNewSet() {
+        return hasNewSet;
+    }
+
+    //
+    // Used in the body of resolve()
+    //
+    private static class MyVisitor extends AbstractJavaHeapObjectVisitor {
+        JavaHeapObject t;
+        public void visit(JavaHeapObject other) {
+            other.addReferenceFrom(t);
+        }
+    }
+
+    // To show heap parsing progress, we print a '.' after this limit
+    private static final int DOT_LIMIT = 5000;
+
+    /**
+     * Called after reading complete, to initialize the structure
+     */
+    public void resolve(boolean calculateRefs) {
+        System.out.println("Resolving " + heapObjects.size() + " objects...");
+
+        // First, resolve the classes.  All classes must be resolved before
+        // we try any objects, because the objects use classes in their
+        // resolution.
+        javaLangClass = findClass("java.lang.Class");
+        if (javaLangClass == null) {
+            System.out.println("WARNING:  hprof file does not include java.lang.Class!");
+            javaLangClass = new JavaClass("java.lang.Class", 0, 0, 0, 0,
+                                 EMPTY_FIELD_ARRAY, EMPTY_STATIC_ARRAY, 0);
+            addFakeClass(javaLangClass);
+        }
+        javaLangString = findClass("java.lang.String");
+        if (javaLangString == null) {
+            System.out.println("WARNING:  hprof file does not include java.lang.String!");
+            javaLangString = new JavaClass("java.lang.String", 0, 0, 0, 0,
+                                 EMPTY_FIELD_ARRAY, EMPTY_STATIC_ARRAY, 0);
+            addFakeClass(javaLangString);
+        }
+        javaLangClassLoader = findClass("java.lang.ClassLoader");
+        if (javaLangClassLoader == null) {
+            System.out.println("WARNING:  hprof file does not include java.lang.ClassLoader!");
+            javaLangClassLoader = new JavaClass("java.lang.ClassLoader", 0, 0, 0, 0,
+                                 EMPTY_FIELD_ARRAY, EMPTY_STATIC_ARRAY, 0);
+            addFakeClass(javaLangClassLoader);
+        }
+
+        for (JavaHeapObject t : heapObjects.values()) {
+            if (t instanceof JavaClass) {
+                t.resolve(this);
+            }
+        }
+
+        // Now, resolve everything else.
+        for (JavaHeapObject t : heapObjects.values()) {
+            if (!(t instanceof JavaClass)) {
+                t.resolve(this);
+            }
+        }
+
+        heapObjects.putAll(fakeClasses);
+        fakeClasses.clear();
+
+        weakReferenceClass = findClass("java.lang.ref.Reference");
+        if (weakReferenceClass == null)  {      // JDK 1.1.x
+            weakReferenceClass = findClass("sun.misc.Ref");
+            referentFieldIndex = 0;
+        } else {
+            JavaField[] fields = weakReferenceClass.getFieldsForInstance();
+            for (int i = 0; i < fields.length; i++) {
+                if ("referent".equals(fields[i].getName())) {
+                    referentFieldIndex = i;
+                    break;
+                }
+            }
+        }
+
+        if (calculateRefs) {
+            calculateReferencesToObjects();
+            System.out.print("Eliminating duplicate references");
+            System.out.flush();
+            // This println refers to the *next* step
+        }
+        int count = 0;
+        for (JavaHeapObject t : heapObjects.values()) {
+            t.setupReferers();
+            ++count;
+            if (calculateRefs && count % DOT_LIMIT == 0) {
+                System.out.print(".");
+                System.out.flush();
+            }
+        }
+        if (calculateRefs) {
+            System.out.println("");
+        }
+
+        // to ensure that Iterator.remove() on getClasses()
+        // result will throw exception..
+        classes = Collections.unmodifiableMap(classes);
+    }
+
+    private void calculateReferencesToObjects() {
+        System.out.print("Chasing references, expect "
+                         + (heapObjects.size() / DOT_LIMIT) + " dots");
+        System.out.flush();
+        int count = 0;
+        MyVisitor visitor = new MyVisitor();
+        for (JavaHeapObject t : heapObjects.values()) {
+            visitor.t = t;
+            // call addReferenceFrom(t) on all objects t references:
+            t.visitReferencedObjects(visitor);
+            ++count;
+            if (count % DOT_LIMIT == 0) {
+                System.out.print(".");
+                System.out.flush();
+            }
+        }
+        System.out.println();
+        for (Root r : roots) {
+            r.resolve(this);
+            JavaHeapObject t = findThing(r.getId());
+            if (t != null) {
+                t.addReferenceFromRoot(r);
+            }
+        }
+    }
+
+    public void markNewRelativeTo(Snapshot baseline) {
+        hasNewSet = true;
+        for (JavaHeapObject t : heapObjects.values()) {
+            boolean isNew;
+            long thingID = t.getId();
+            if (thingID == 0L || thingID == -1L) {
+                isNew = false;
+            } else {
+                JavaThing other = baseline.findThing(t.getId());
+                if (other == null) {
+                    isNew = true;
+                } else {
+                    isNew = !t.isSameTypeAs(other);
+                }
+            }
+            t.setNew(isNew);
+        }
+    }
+
+    public Enumeration<JavaHeapObject> getThings() {
+        return heapObjects.elements();
+    }
+
+
+    public JavaHeapObject findThing(long id) {
+        Number idObj = makeId(id);
+        JavaHeapObject jho = heapObjects.get(idObj);
+        return jho != null? jho : fakeClasses.get(idObj);
+    }
+
+    public JavaHeapObject findThing(String id) {
+        return findThing(Misc.parseHex(id));
+    }
+
+    public JavaClass findClass(String name) {
+        if (name.startsWith("0x")) {
+            return (JavaClass) findThing(name);
+        } else {
+            return classes.get(name);
+        }
+    }
+
+    /**
+     * Return an Iterator of all of the classes in this snapshot.
+     **/
+    public Iterator<JavaClass> getClasses() {
+        // note that because classes is a TreeMap
+        // classes are already sorted by name
+        return classes.values().iterator();
+    }
+
+    public JavaClass[] getClassesArray() {
+        JavaClass[] res = new JavaClass[classes.size()];
+        classes.values().toArray(res);
+        return res;
+    }
+
+    public synchronized Enumeration<?> getFinalizerObjects() {
+        Vector<?> obj;
+        if (finalizablesCache != null &&
+            (obj = finalizablesCache.get()) != null) {
+            return obj.elements();
+        }
+
+        JavaClass clazz = findClass("java.lang.ref.Finalizer");
+        JavaObject queue = (JavaObject) clazz.getStaticField("queue");
+        JavaThing tmp = queue.getField("head");
+        Vector<JavaHeapObject> finalizables = new Vector<JavaHeapObject>();
+        if (tmp != getNullThing()) {
+            JavaObject head = (JavaObject) tmp;
+            while (true) {
+                JavaHeapObject referent = (JavaHeapObject) head.getField("referent");
+                JavaThing next = head.getField("next");
+                if (next == getNullThing() || next.equals(head)) {
+                    break;
+                }
+                head = (JavaObject) next;
+                finalizables.add(referent);
+            }
+        }
+        finalizablesCache = new SoftReference<Vector<?>>(finalizables);
+        return finalizables.elements();
+    }
+
+    public Enumeration<Root> getRoots() {
+        return roots.elements();
+    }
+
+    public Root[] getRootsArray() {
+        Root[] res = new Root[roots.size()];
+        roots.toArray(res);
+        return res;
+    }
+
+    public Root getRootAt(int i) {
+        return roots.elementAt(i);
+    }
+
+    public ReferenceChain[]
+    rootsetReferencesTo(JavaHeapObject target, boolean includeWeak) {
+        Vector<ReferenceChain> fifo = new Vector<ReferenceChain>();  // This is slow... A real fifo would help
+            // Must be a fifo to go breadth-first
+        Hashtable<JavaHeapObject, JavaHeapObject> visited = new Hashtable<JavaHeapObject, JavaHeapObject>();
+        // Objects are added here right after being added to fifo.
+        Vector<ReferenceChain> result = new Vector<ReferenceChain>();
+        visited.put(target, target);
+        fifo.addElement(new ReferenceChain(target, null));
+
+        while (fifo.size() > 0) {
+            ReferenceChain chain = fifo.elementAt(0);
+            fifo.removeElementAt(0);
+            JavaHeapObject curr = chain.getObj();
+            if (curr.getRoot() != null) {
+                result.addElement(chain);
+                // Even though curr is in the rootset, we want to explore its
+                // referers, because they might be more interesting.
+            }
+            Enumeration<JavaThing> referers = curr.getReferers();
+            while (referers.hasMoreElements()) {
+                JavaHeapObject t = (JavaHeapObject) referers.nextElement();
+                if (t != null && !visited.containsKey(t)) {
+                    if (includeWeak || !t.refersOnlyWeaklyTo(this, curr)) {
+                        visited.put(t, t);
+                        fifo.addElement(new ReferenceChain(t, chain));
+                    }
+                }
+            }
+        }
+
+        ReferenceChain[] realResult = new ReferenceChain[result.size()];
+        for (int i = 0; i < result.size(); i++) {
+            realResult[i] =  result.elementAt(i);
+        }
+        return realResult;
+    }
+
+    public boolean getUnresolvedObjectsOK() {
+        return unresolvedObjectsOK;
+    }
+
+    public void setUnresolvedObjectsOK(boolean v) {
+        unresolvedObjectsOK = v;
+    }
+
+    public JavaClass getWeakReferenceClass() {
+        return weakReferenceClass;
+    }
+
+    public int getReferentFieldIndex() {
+        return referentFieldIndex;
+    }
+
+    public JavaThing getNullThing() {
+        return nullThing;
+    }
+
+    public void setReachableExcludes(ReachableExcludes e) {
+        reachableExcludes = e;
+    }
+
+    public ReachableExcludes getReachableExcludes() {
+        return reachableExcludes;
+    }
+
+    // package privates
+    void addReferenceFromRoot(Root r, JavaHeapObject obj) {
+        Root root = rootsMap.get(obj);
+        if (root == null) {
+            rootsMap.put(obj, r);
+        } else {
+            rootsMap.put(obj, root.mostInteresting(r));
+        }
+    }
+
+    Root getRoot(JavaHeapObject obj) {
+        return rootsMap.get(obj);
+    }
+
+    JavaClass getJavaLangClass() {
+        return javaLangClass;
+    }
+
+    JavaClass getJavaLangString() {
+        return javaLangString;
+    }
+
+    JavaClass getJavaLangClassLoader() {
+        return javaLangClassLoader;
+    }
+
+    JavaClass getOtherArrayType() {
+        if (otherArrayType == null) {
+            synchronized(this) {
+                if (otherArrayType == null) {
+                    addFakeClass(new JavaClass("[<other>", 0, 0, 0, 0,
+                                     EMPTY_FIELD_ARRAY, EMPTY_STATIC_ARRAY,
+                                     0));
+                    otherArrayType = findClass("[<other>");
+                }
+            }
+        }
+        return otherArrayType;
+    }
+
+    JavaClass getArrayClass(String elementSignature) {
+        JavaClass clazz;
+        synchronized(classes) {
+            clazz = findClass("[" + elementSignature);
+            if (clazz == null) {
+                clazz = new JavaClass("[" + elementSignature, 0, 0, 0, 0,
+                                   EMPTY_FIELD_ARRAY, EMPTY_STATIC_ARRAY, 0);
+                addFakeClass(clazz);
+                // This is needed because the JDK only creates Class structures
+                // for array element types, not the arrays themselves.  For
+                // analysis, though, we need to pretend that there's a
+                // JavaClass for the array type, too.
+            }
+        }
+        return clazz;
+    }
+
+    ReadBuffer getReadBuffer() {
+        return readBuf;
+    }
+
+    void setNew(JavaHeapObject obj, boolean isNew) {
+        initNewObjects();
+        if (isNew) {
+            newObjects.put(obj, Boolean.TRUE);
+        }
+    }
+
+    boolean isNew(JavaHeapObject obj) {
+        if (newObjects != null) {
+            return newObjects.get(obj) != null;
+        } else {
+            return false;
+        }
+    }
+
+    // Internals only below this point
+    private Number makeId(long id) {
+        if (identifierSize == 4) {
+            return (int)id;
+        } else {
+            return id;
+        }
+    }
+
+    private void putInClassesMap(JavaClass c) {
+        String name = c.getName();
+        if (classes.containsKey(name)) {
+            // more than one class can have the same name
+            // if so, create a unique name by appending
+            // - and id string to it.
+            name += "-" + c.getIdString();
+        }
+        classes.put(c.getName(), c);
+    }
+
+    private void addFakeClass(JavaClass c) {
+        putInClassesMap(c);
+        c.resolve(this);
+    }
+
+    private void addFakeClass(Number id, JavaClass c) {
+        fakeClasses.put(id, c);
+        addFakeClass(c);
+    }
+
+    private synchronized void initNewObjects() {
+        if (newObjects == null) {
+            synchronized (this) {
+                if (newObjects == null) {
+                    newObjects = new HashMap<JavaHeapObject, Boolean>();
+                }
+            }
+        }
+    }
+
+    private synchronized void initSiteTraces() {
+        if (siteTraces == null) {
+            synchronized (this) {
+                if (siteTraces == null) {
+                    siteTraces = new HashMap<JavaHeapObject, StackTrace>();
+                }
+            }
+        }
+    }
+
+    @Override
+    public void close() throws Exception {
+        readBuf.close();
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/StackFrame.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,101 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+/**
+ *
+ * @author      Bill Foote
+ */
+
+
+/**
+ * Represents a stack frame.
+ */
+
+public class StackFrame {
+
+    //
+    // Values for the lineNumber data member.  These are the same
+    // as the values used in the JDK 1.2 heap dump file.
+    //
+    public final static int LINE_NUMBER_UNKNOWN = -1;
+    public final static int LINE_NUMBER_COMPILED = -2;
+    public final static int LINE_NUMBER_NATIVE = -3;
+
+    private String methodName;
+    private String methodSignature;
+    private String className;
+    private String sourceFileName;
+    private int lineNumber;
+
+    public StackFrame(String methodName, String methodSignature,
+                      String className, String sourceFileName, int lineNumber) {
+        this.methodName = methodName;
+        this.methodSignature = methodSignature;
+        this.className = className;
+        this.sourceFileName = sourceFileName;
+        this.lineNumber = lineNumber;
+    }
+
+    public void resolve(Snapshot snapshot) {
+    }
+
+    public String getMethodName() {
+        return methodName;
+    }
+
+    public String getMethodSignature() {
+        return methodSignature;
+    }
+
+    public String getClassName() {
+        return className;
+    }
+
+    public String getSourceFileName() {
+        return sourceFileName;
+    }
+
+    public String getLineNumber() {
+        switch(lineNumber) {
+            case LINE_NUMBER_UNKNOWN:
+                return "(unknown)";
+            case LINE_NUMBER_COMPILED:
+                return "(compiled method)";
+            case LINE_NUMBER_NATIVE:
+                return "(native method)";
+            default:
+                return Integer.toString(lineNumber, 10);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/model/StackTrace.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,77 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.model;
+
+/**
+ *
+ * @author      Bill Foote
+ */
+
+
+/**
+ * Represents a stack trace, that is, an ordered collection of stack frames.
+ */
+
+public class StackTrace {
+
+    private StackFrame[] frames;
+
+    public StackTrace(StackFrame[] frames) {
+        this.frames = frames;
+    }
+
+    /**
+     * @param depth.  The minimum reasonable depth is 1.
+     *
+     * @return a (possibly new) StackTrace that is limited to depth.
+     */
+    public StackTrace traceForDepth(int depth) {
+        if (depth >= frames.length) {
+            return this;
+        } else {
+            StackFrame[] f = new StackFrame[depth];
+            System.arraycopy(frames, 0, f, 0, depth);
+            return new StackTrace(f);
+        }
+    }
+
+    public void resolve(Snapshot snapshot) {
+        for (int i = 0; i < frames.length; i++) {
+            frames[i].resolve(snapshot);
+        }
+    }
+
+    public StackFrame[] getFrames() {
+        return frames;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/parser/FileReadBuffer.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,89 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.parser;
+
+import java.io.IOException;
+import java.io.RandomAccessFile;
+
+/**
+ * Implementation of ReadBuffer using a RandomAccessFile
+ *
+ * @author A. Sundararajan
+ */
+class FileReadBuffer implements ReadBuffer {
+    // underlying file to read
+    private RandomAccessFile file;
+
+    FileReadBuffer(RandomAccessFile file) {
+        this.file = file;
+    }
+
+    private void seek(long pos) throws IOException {
+        file.getChannel().position(pos);
+    }
+
+    public synchronized void get(long pos, byte[] buf) throws IOException {
+        seek(pos);
+        file.read(buf);
+    }
+
+    public synchronized char getChar(long pos) throws IOException {
+        seek(pos);
+        return file.readChar();
+    }
+
+    public synchronized byte getByte(long pos) throws IOException {
+        seek(pos);
+        return (byte) file.read();
+    }
+
+    public synchronized short getShort(long pos) throws IOException {
+        seek(pos);
+        return file.readShort();
+    }
+
+    public synchronized int getInt(long pos) throws IOException {
+        seek(pos);
+        return file.readInt();
+    }
+
+    public synchronized long getLong(long pos) throws IOException {
+        seek(pos);
+        return file.readLong();
+    }
+
+    @Override
+    public void close() throws Exception {
+        file.close();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/parser/HprofReader.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,892 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.parser;
+
+import java.io.*;
+import java.util.Date;
+import java.util.Hashtable;
+import jdk.test.lib.hprof.model.ArrayTypeCodes;
+import jdk.test.lib.hprof.model.*;
+
+/**
+ * Object that's used to read a hprof file.
+ *
+ * @author      Bill Foote
+ */
+
+public class HprofReader extends Reader /* imports */ implements ArrayTypeCodes {
+
+    final static int MAGIC_NUMBER = 0x4a415641;
+    // That's "JAVA", the first part of "JAVA PROFILE ..."
+    private final static String[] VERSIONS = {
+            " PROFILE 1.0\0",
+            " PROFILE 1.0.1\0",
+            " PROFILE 1.0.2\0",
+    };
+
+    private final static int VERSION_JDK12BETA3 = 0;
+    private final static int VERSION_JDK12BETA4 = 1;
+    private final static int VERSION_JDK6       = 2;
+    // These version numbers are indices into VERSIONS.  The instance data
+    // member version is set to one of these, and it drives decisions when
+    // reading the file.
+    //
+    // Version 1.0.1 added HPROF_GC_PRIM_ARRAY_DUMP, which requires no
+    // version-sensitive parsing.
+    //
+    // Version 1.0.1 changed the type of a constant pool entry from a signature
+    // to a typecode.
+    //
+    // Version 1.0.2 added HPROF_HEAP_DUMP_SEGMENT and HPROF_HEAP_DUMP_END
+    // to allow a large heap to be dumped as a sequence of heap dump segments.
+    //
+    // The HPROF agent in J2SE 1.2 through to 5.0 generate a version 1.0.1
+    // file. In Java SE 6.0 the version is either 1.0.1 or 1.0.2 depending on
+    // the size of the heap (normally it will be 1.0.1 but for multi-GB
+    // heaps the heap dump will not fit in a HPROF_HEAP_DUMP record so the
+    // dump is generated as version 1.0.2).
+
+    //
+    // Record types:
+    //
+    static final int HPROF_UTF8          = 0x01;
+    static final int HPROF_LOAD_CLASS    = 0x02;
+    static final int HPROF_UNLOAD_CLASS  = 0x03;
+    static final int HPROF_FRAME         = 0x04;
+    static final int HPROF_TRACE         = 0x05;
+    static final int HPROF_ALLOC_SITES   = 0x06;
+    static final int HPROF_HEAP_SUMMARY  = 0x07;
+
+    static final int HPROF_START_THREAD  = 0x0a;
+    static final int HPROF_END_THREAD    = 0x0b;
+
+    static final int HPROF_HEAP_DUMP     = 0x0c;
+
+    static final int HPROF_CPU_SAMPLES   = 0x0d;
+    static final int HPROF_CONTROL_SETTINGS = 0x0e;
+    static final int HPROF_LOCKSTATS_WAIT_TIME = 0x10;
+    static final int HPROF_LOCKSTATS_HOLD_TIME = 0x11;
+
+    static final int HPROF_GC_ROOT_UNKNOWN       = 0xff;
+    static final int HPROF_GC_ROOT_JNI_GLOBAL    = 0x01;
+    static final int HPROF_GC_ROOT_JNI_LOCAL     = 0x02;
+    static final int HPROF_GC_ROOT_JAVA_FRAME    = 0x03;
+    static final int HPROF_GC_ROOT_NATIVE_STACK  = 0x04;
+    static final int HPROF_GC_ROOT_STICKY_CLASS  = 0x05;
+    static final int HPROF_GC_ROOT_THREAD_BLOCK  = 0x06;
+    static final int HPROF_GC_ROOT_MONITOR_USED  = 0x07;
+    static final int HPROF_GC_ROOT_THREAD_OBJ    = 0x08;
+
+    static final int HPROF_GC_CLASS_DUMP         = 0x20;
+    static final int HPROF_GC_INSTANCE_DUMP      = 0x21;
+    static final int HPROF_GC_OBJ_ARRAY_DUMP         = 0x22;
+    static final int HPROF_GC_PRIM_ARRAY_DUMP         = 0x23;
+
+    static final int HPROF_HEAP_DUMP_SEGMENT     = 0x1c;
+    static final int HPROF_HEAP_DUMP_END         = 0x2c;
+
+    private final static int T_CLASS = 2;
+
+    private int version;        // The version of .hprof being read
+
+    private int debugLevel;
+    private long currPos;        // Current position in the file
+
+    private int dumpsToSkip;
+    private boolean callStack;  // If true, read the call stack of objects
+
+    private int identifierSize;         // Size, in bytes, of identifiers.
+    private Hashtable<Long, String> names;
+
+    // Hashtable<Integer, ThreadObject>, used to map the thread sequence number
+    // (aka "serial number") to the thread object ID for
+    // HPROF_GC_ROOT_THREAD_OBJ.  ThreadObject is a trivial inner class,
+    // at the end of this file.
+    private Hashtable<Integer, ThreadObject> threadObjects;
+
+    // Hashtable<Long, String>, maps class object ID to class name
+    // (with / converted to .)
+    private Hashtable<Long, String> classNameFromObjectID;
+
+    // Hashtable<Integer, Integer>, maps class serial # to class object ID
+    private Hashtable<Integer, String> classNameFromSerialNo;
+
+    // Hashtable<Long, StackFrame> maps stack frame ID to StackFrame.
+    // Null if we're not tracking them.
+    private Hashtable<Long, StackFrame> stackFrames;
+
+    // Hashtable<Integer, StackTrace> maps stack frame ID to StackTrace
+    // Null if we're not tracking them.
+    private Hashtable<Integer, StackTrace> stackTraces;
+
+    private Snapshot snapshot;
+
+    public HprofReader(String fileName, PositionDataInputStream in,
+                       int dumpNumber, boolean callStack, int debugLevel)
+                       throws IOException {
+        super(in);
+        RandomAccessFile file = new RandomAccessFile(fileName, "r");
+        this.snapshot = new Snapshot(MappedReadBuffer.create(file));
+        this.dumpsToSkip = dumpNumber - 1;
+        this.callStack = callStack;
+        this.debugLevel = debugLevel;
+        names = new Hashtable<Long, String>();
+        threadObjects = new Hashtable<Integer, ThreadObject>(43);
+        classNameFromObjectID = new Hashtable<Long, String>();
+        if (callStack) {
+            stackFrames = new Hashtable<Long, StackFrame>(43);
+            stackTraces = new Hashtable<Integer, StackTrace>(43);
+            classNameFromSerialNo = new Hashtable<Integer, String>();
+        }
+    }
+
+    public Snapshot read() throws IOException {
+        currPos = 4;    // 4 because of the magic number
+        version = readVersionHeader();
+        identifierSize = in.readInt();
+        snapshot.setIdentifierSize(identifierSize);
+        if (version >= VERSION_JDK12BETA4) {
+            snapshot.setNewStyleArrayClass(true);
+        } else {
+            snapshot.setNewStyleArrayClass(false);
+        }
+
+        currPos += 4;
+        if (identifierSize != 4 && identifierSize != 8) {
+            throw new IOException("I'm sorry, but I can't deal with an identifier size of " + identifierSize + ".  I can only deal with 4 or 8.");
+        }
+        System.out.println("Dump file created " + (new Date(in.readLong())));
+        currPos += 8;
+
+        for (;;) {
+            int type;
+            try {
+                type = in.readUnsignedByte();
+            } catch (EOFException ignored) {
+                break;
+            }
+            in.readInt();       // Timestamp of this record
+            // Length of record: readInt() will return negative value for record
+            // length >2GB.  so store 32bit value in long to keep it unsigned.
+            long length = in.readInt() & 0xffffffffL;
+            if (debugLevel > 0) {
+                System.out.println("Read record type " + type
+                                   + ", length " + length
+                                   + " at position " + toHex(currPos));
+            }
+            if (length < 0) {
+                throw new IOException("Bad record length of " + length
+                                      + " at byte " + toHex(currPos+5)
+                                      + " of file.");
+            }
+            currPos += 9 + length;
+            switch (type) {
+                case HPROF_UTF8: {
+                    long id = readID();
+                    byte[] chars = new byte[(int)length - identifierSize];
+                    in.readFully(chars);
+                    names.put(id, new String(chars));
+                    break;
+                }
+                case HPROF_LOAD_CLASS: {
+                    int serialNo = in.readInt();        // Not used
+                    long classID = readID();
+                    int stackTraceSerialNo = in.readInt();
+                    long classNameID = readID();
+                    Long classIdI = classID;
+                    String nm = getNameFromID(classNameID).replace('/', '.');
+                    classNameFromObjectID.put(classIdI, nm);
+                    if (classNameFromSerialNo != null) {
+                        classNameFromSerialNo.put(serialNo, nm);
+                    }
+                    break;
+                }
+
+                case HPROF_HEAP_DUMP: {
+                    if (dumpsToSkip <= 0) {
+                        try {
+                            readHeapDump(length, currPos);
+                        } catch (EOFException exp) {
+                            handleEOF(exp, snapshot);
+                        }
+                        if (debugLevel > 0) {
+                            System.out.println("    Finished processing instances in heap dump.");
+                        }
+                        return snapshot;
+                    } else {
+                        dumpsToSkip--;
+                        skipBytes(length);
+                    }
+                    break;
+                }
+
+                case HPROF_HEAP_DUMP_END: {
+                    if (version >= VERSION_JDK6) {
+                        if (dumpsToSkip <= 0) {
+                            skipBytes(length);  // should be no-op
+                            return snapshot;
+                        } else {
+                            // skip this dump (of the end record for a sequence of dump segments)
+                            dumpsToSkip--;
+                        }
+                    } else {
+                        // HPROF_HEAP_DUMP_END only recognized in >= 1.0.2
+                        warn("Ignoring unrecognized record type " + type);
+                    }
+                    skipBytes(length);  // should be no-op
+                    break;
+                }
+
+                case HPROF_HEAP_DUMP_SEGMENT: {
+                    if (version >= VERSION_JDK6) {
+                        if (dumpsToSkip <= 0) {
+                            try {
+                                // read the dump segment
+                                readHeapDump(length, currPos);
+                            } catch (EOFException exp) {
+                                handleEOF(exp, snapshot);
+                            }
+                        } else {
+                            // all segments comprising the heap dump will be skipped
+                            skipBytes(length);
+                        }
+                    } else {
+                        // HPROF_HEAP_DUMP_SEGMENT only recognized in >= 1.0.2
+                        warn("Ignoring unrecognized record type " + type);
+                        skipBytes(length);
+                    }
+                    break;
+                }
+
+                case HPROF_FRAME: {
+                    if (stackFrames == null) {
+                        skipBytes(length);
+                    } else {
+                        long id = readID();
+                        String methodName = getNameFromID(readID());
+                        String methodSig = getNameFromID(readID());
+                        String sourceFile = getNameFromID(readID());
+                        int classSer = in.readInt();
+                        String className = classNameFromSerialNo.get(classSer);
+                        int lineNumber = in.readInt();
+                        if (lineNumber < StackFrame.LINE_NUMBER_NATIVE) {
+                            warn("Weird stack frame line number:  " + lineNumber);
+                            lineNumber = StackFrame.LINE_NUMBER_UNKNOWN;
+                        }
+                        stackFrames.put(id,
+                                        new StackFrame(methodName, methodSig,
+                                                       className, sourceFile,
+                                                       lineNumber));
+                    }
+                    break;
+                }
+                case HPROF_TRACE: {
+                    if (stackTraces == null) {
+                        skipBytes(length);
+                    } else {
+                        int serialNo = in.readInt();
+                        int threadSeq = in.readInt();   // Not used
+                        StackFrame[] frames = new StackFrame[in.readInt()];
+                        for (int i = 0; i < frames.length; i++) {
+                            long fid = readID();
+                            frames[i] = stackFrames.get(fid);
+                            if (frames[i] == null) {
+                                throw new IOException("Stack frame " + toHex(fid) + " not found");
+                            }
+                        }
+                        stackTraces.put(serialNo,
+                                        new StackTrace(frames));
+                    }
+                    break;
+                }
+                case HPROF_UNLOAD_CLASS:
+                case HPROF_ALLOC_SITES:
+                case HPROF_START_THREAD:
+                case HPROF_END_THREAD:
+                case HPROF_HEAP_SUMMARY:
+                case HPROF_CPU_SAMPLES:
+                case HPROF_CONTROL_SETTINGS:
+                case HPROF_LOCKSTATS_WAIT_TIME:
+                case HPROF_LOCKSTATS_HOLD_TIME:
+                {
+                    // Ignore these record types
+                    skipBytes(length);
+                    break;
+                }
+                default: {
+                    skipBytes(length);
+                    warn("Ignoring unrecognized record type " + type);
+                }
+            }
+        }
+
+        return snapshot;
+    }
+
+    private void skipBytes(long length) throws IOException {
+        in.skipBytes((int)length);
+    }
+
+    private int readVersionHeader() throws IOException {
+        int candidatesLeft = VERSIONS.length;
+        boolean[] matched = new boolean[VERSIONS.length];
+        for (int i = 0; i < candidatesLeft; i++) {
+            matched[i] = true;
+        }
+
+        int pos = 0;
+        while (candidatesLeft > 0) {
+            char c = (char) in.readByte();
+            currPos++;
+            for (int i = 0; i < VERSIONS.length; i++) {
+                if (matched[i]) {
+                    if (c != VERSIONS[i].charAt(pos)) {   // Not matched
+                        matched[i] = false;
+                        --candidatesLeft;
+                    } else if (pos == VERSIONS[i].length() - 1) {  // Full match
+                        return i;
+                    }
+                }
+            }
+            ++pos;
+        }
+        throw new IOException("Version string not recognized at byte " + (pos+3));
+    }
+
+    private void readHeapDump(long bytesLeft, long posAtEnd) throws IOException {
+        while (bytesLeft > 0) {
+            int type = in.readUnsignedByte();
+            if (debugLevel > 0) {
+                System.out.println("    Read heap sub-record type " + type
+                                   + " at position "
+                                   + toHex(posAtEnd - bytesLeft));
+            }
+            bytesLeft--;
+            switch(type) {
+                case HPROF_GC_ROOT_UNKNOWN: {
+                    long id = readID();
+                    bytesLeft -= identifierSize;
+                    snapshot.addRoot(new Root(id, 0, Root.UNKNOWN, ""));
+                    break;
+                }
+                case HPROF_GC_ROOT_THREAD_OBJ: {
+                    long id = readID();
+                    int threadSeq = in.readInt();
+                    int stackSeq = in.readInt();
+                    bytesLeft -= identifierSize + 8;
+                    threadObjects.put(threadSeq,
+                                      new ThreadObject(id, stackSeq));
+                    break;
+                }
+                case HPROF_GC_ROOT_JNI_GLOBAL: {
+                    long id = readID();
+                    long globalRefId = readID();        // Ignored, for now
+                    bytesLeft -= 2*identifierSize;
+                    snapshot.addRoot(new Root(id, 0, Root.NATIVE_STATIC, ""));
+                    break;
+                }
+                case HPROF_GC_ROOT_JNI_LOCAL: {
+                    long id = readID();
+                    int threadSeq = in.readInt();
+                    int depth = in.readInt();
+                    bytesLeft -= identifierSize + 8;
+                    ThreadObject to = getThreadObjectFromSequence(threadSeq);
+                    StackTrace st = getStackTraceFromSerial(to.stackSeq);
+                    if (st != null) {
+                        st = st.traceForDepth(depth+1);
+                    }
+                    snapshot.addRoot(new Root(id, to.threadId,
+                                              Root.NATIVE_LOCAL, "", st));
+                    break;
+                }
+                case HPROF_GC_ROOT_JAVA_FRAME: {
+                    long id = readID();
+                    int threadSeq = in.readInt();
+                    int depth = in.readInt();
+                    bytesLeft -= identifierSize + 8;
+                    ThreadObject to = getThreadObjectFromSequence(threadSeq);
+                    StackTrace st = getStackTraceFromSerial(to.stackSeq);
+                    if (st != null) {
+                        st = st.traceForDepth(depth+1);
+                    }
+                    snapshot.addRoot(new Root(id, to.threadId,
+                                              Root.JAVA_LOCAL, "", st));
+                    break;
+                }
+                case HPROF_GC_ROOT_NATIVE_STACK: {
+                    long id = readID();
+                    int threadSeq = in.readInt();
+                    bytesLeft -= identifierSize + 4;
+                    ThreadObject to = getThreadObjectFromSequence(threadSeq);
+                    StackTrace st = getStackTraceFromSerial(to.stackSeq);
+                    snapshot.addRoot(new Root(id, to.threadId,
+                                              Root.NATIVE_STACK, "", st));
+                    break;
+                }
+                case HPROF_GC_ROOT_STICKY_CLASS: {
+                    long id = readID();
+                    bytesLeft -= identifierSize;
+                    snapshot.addRoot(new Root(id, 0, Root.SYSTEM_CLASS, ""));
+                    break;
+                }
+                case HPROF_GC_ROOT_THREAD_BLOCK: {
+                    long id = readID();
+                    int threadSeq = in.readInt();
+                    bytesLeft -= identifierSize + 4;
+                    ThreadObject to = getThreadObjectFromSequence(threadSeq);
+                    StackTrace st = getStackTraceFromSerial(to.stackSeq);
+                    snapshot.addRoot(new Root(id, to.threadId,
+                                     Root.THREAD_BLOCK, "", st));
+                    break;
+                }
+                case HPROF_GC_ROOT_MONITOR_USED: {
+                    long id = readID();
+                    bytesLeft -= identifierSize;
+                    snapshot.addRoot(new Root(id, 0, Root.BUSY_MONITOR, ""));
+                    break;
+                }
+                case HPROF_GC_CLASS_DUMP: {
+                    int bytesRead = readClass();
+                    bytesLeft -= bytesRead;
+                    break;
+                }
+                case HPROF_GC_INSTANCE_DUMP: {
+                    int bytesRead = readInstance();
+                    bytesLeft -= bytesRead;
+                    break;
+                }
+                case HPROF_GC_OBJ_ARRAY_DUMP: {
+                    int bytesRead = readArray(false);
+                    bytesLeft -= bytesRead;
+                    break;
+                }
+                case HPROF_GC_PRIM_ARRAY_DUMP: {
+                    int bytesRead = readArray(true);
+                    bytesLeft -= bytesRead;
+                    break;
+                }
+                default: {
+                    throw new IOException("Unrecognized heap dump sub-record type:  " + type);
+                }
+            }
+        }
+        if (bytesLeft != 0) {
+            warn("Error reading heap dump or heap dump segment:  Byte count is " + bytesLeft + " instead of 0");
+            skipBytes(bytesLeft);
+        }
+        if (debugLevel > 0) {
+            System.out.println("    Finished heap sub-records.");
+        }
+    }
+
+    private long readID() throws IOException {
+        return (identifierSize == 4)?
+            (Snapshot.SMALL_ID_MASK & (long)in.readInt()) : in.readLong();
+    }
+
+    //
+    // Read a java value.  If result is non-null, it's expected to be an
+    // array of one element.  We use it to fake multiple return values.
+    // @returns the number of bytes read
+    //
+    private int readValue(JavaThing[] resultArr) throws IOException {
+        byte type = in.readByte();
+        return 1 + readValueForType(type, resultArr);
+    }
+
+    private int readValueForType(byte type, JavaThing[] resultArr)
+            throws IOException {
+        if (version >= VERSION_JDK12BETA4) {
+            type = signatureFromTypeId(type);
+        }
+        return readValueForTypeSignature(type, resultArr);
+    }
+
+    private int readValueForTypeSignature(byte type, JavaThing[] resultArr)
+            throws IOException {
+        switch (type) {
+            case '[':
+            case 'L': {
+                long id = readID();
+                if (resultArr != null) {
+                    resultArr[0] = new JavaObjectRef(id);
+                }
+                return identifierSize;
+            }
+            case 'Z': {
+                int b = in.readByte();
+                if (b != 0 && b != 1) {
+                    warn("Illegal boolean value read");
+                }
+                if (resultArr != null) {
+                    resultArr[0] = new JavaBoolean(b != 0);
+                }
+                return 1;
+            }
+            case 'B': {
+                byte b = in.readByte();
+                if (resultArr != null) {
+                    resultArr[0] = new JavaByte(b);
+                }
+                return 1;
+            }
+            case 'S': {
+                short s = in.readShort();
+                if (resultArr != null) {
+                    resultArr[0] = new JavaShort(s);
+                }
+                return 2;
+            }
+            case 'C': {
+                char ch = in.readChar();
+                if (resultArr != null) {
+                    resultArr[0] = new JavaChar(ch);
+                }
+                return 2;
+            }
+            case 'I': {
+                int val = in.readInt();
+                if (resultArr != null) {
+                    resultArr[0] = new JavaInt(val);
+                }
+                return 4;
+            }
+            case 'J': {
+                long val = in.readLong();
+                if (resultArr != null) {
+                    resultArr[0] = new JavaLong(val);
+                }
+                return 8;
+            }
+            case 'F': {
+                float val = in.readFloat();
+                if (resultArr != null) {
+                    resultArr[0] = new JavaFloat(val);
+                }
+                return 4;
+            }
+            case 'D': {
+                double val = in.readDouble();
+                if (resultArr != null) {
+                    resultArr[0] = new JavaDouble(val);
+                }
+                return 8;
+            }
+            default: {
+                throw new IOException("Bad value signature:  " + type);
+            }
+        }
+    }
+
+    private ThreadObject getThreadObjectFromSequence(int threadSeq)
+            throws IOException {
+        ThreadObject to = threadObjects.get(threadSeq);
+        if (to == null) {
+            throw new IOException("Thread " + threadSeq +
+                                  " not found for JNI local ref");
+        }
+        return to;
+    }
+
+    private String getNameFromID(long id) throws IOException {
+        return getNameFromID(Long.valueOf(id));
+    }
+
+    private String getNameFromID(Long id) throws IOException {
+        if (id.longValue() == 0L) {
+            return "";
+        }
+        String result = names.get(id);
+        if (result == null) {
+            warn("Name not found at " + toHex(id.longValue()));
+            return "unresolved name " + toHex(id.longValue());
+        }
+        return result;
+    }
+
+    private StackTrace getStackTraceFromSerial(int ser) throws IOException {
+        if (stackTraces == null) {
+            return null;
+        }
+        StackTrace result = stackTraces.get(ser);
+        if (result == null) {
+            warn("Stack trace not found for serial # " + ser);
+        }
+        return result;
+    }
+
+    //
+    // Handle a HPROF_GC_CLASS_DUMP
+    // Return number of bytes read
+    //
+    private int readClass() throws IOException {
+        long id = readID();
+        StackTrace stackTrace = getStackTraceFromSerial(in.readInt());
+        long superId = readID();
+        long classLoaderId = readID();
+        long signersId = readID();
+        long protDomainId = readID();
+        long reserved1 = readID();
+        long reserved2 = readID();
+        int instanceSize = in.readInt();
+        int bytesRead = 7 * identifierSize + 8;
+
+        int numConstPoolEntries = in.readUnsignedShort();
+        bytesRead += 2;
+        for (int i = 0; i < numConstPoolEntries; i++) {
+            int index = in.readUnsignedShort(); // unused
+            bytesRead += 2;
+            bytesRead += readValue(null);       // We ignore the values
+        }
+
+        int numStatics = in.readUnsignedShort();
+        bytesRead += 2;
+        JavaThing[] valueBin = new JavaThing[1];
+        JavaStatic[] statics = new JavaStatic[numStatics];
+        for (int i = 0; i < numStatics; i++) {
+            long nameId = readID();
+            bytesRead += identifierSize;
+            byte type = in.readByte();
+            bytesRead++;
+            bytesRead += readValueForType(type, valueBin);
+            String fieldName = getNameFromID(nameId);
+            if (version >= VERSION_JDK12BETA4) {
+                type = signatureFromTypeId(type);
+            }
+            String signature = "" + ((char) type);
+            JavaField f = new JavaField(fieldName, signature);
+            statics[i] = new JavaStatic(f, valueBin[0]);
+        }
+
+        int numFields = in.readUnsignedShort();
+        bytesRead += 2;
+        JavaField[] fields = new JavaField[numFields];
+        for (int i = 0; i < numFields; i++) {
+            long nameId = readID();
+            bytesRead += identifierSize;
+            byte type = in.readByte();
+            bytesRead++;
+            String fieldName = getNameFromID(nameId);
+            if (version >= VERSION_JDK12BETA4) {
+                type = signatureFromTypeId(type);
+            }
+            String signature = "" + ((char) type);
+            fields[i] = new JavaField(fieldName, signature);
+        }
+        String name = classNameFromObjectID.get(id);
+        if (name == null) {
+            warn("Class name not found for " + toHex(id));
+            name = "unknown-name@" + toHex(id);
+        }
+        JavaClass c = new JavaClass(id, name, superId, classLoaderId, signersId,
+                                    protDomainId, fields, statics,
+                                    instanceSize);
+        snapshot.addClass(id, c);
+        snapshot.setSiteTrace(c, stackTrace);
+
+        return bytesRead;
+    }
+
+    private String toHex(long addr) {
+        return jdk.test.lib.hprof.util.Misc.toHex(addr);
+    }
+
+    //
+    // Handle a HPROF_GC_INSTANCE_DUMP
+    // Return number of bytes read
+    //
+    private int readInstance() throws IOException {
+        long start = in.position();
+        long id = readID();
+        StackTrace stackTrace = getStackTraceFromSerial(in.readInt());
+        long classID = readID();
+        int bytesFollowing = in.readInt();
+        int bytesRead = (2 * identifierSize) + 8 + bytesFollowing;
+        JavaObject jobj = new JavaObject(classID, start);
+        skipBytes(bytesFollowing);
+        snapshot.addHeapObject(id, jobj);
+        snapshot.setSiteTrace(jobj, stackTrace);
+        return bytesRead;
+    }
+
+    //
+    // Handle a HPROF_GC_OBJ_ARRAY_DUMP or HPROF_GC_PRIM_ARRAY_DUMP
+    // Return number of bytes read
+    //
+    private int readArray(boolean isPrimitive) throws IOException {
+        long start = in.position();
+        long id = readID();
+        StackTrace stackTrace = getStackTraceFromSerial(in.readInt());
+        int num = in.readInt();
+        int bytesRead = identifierSize + 8;
+        long elementClassID;
+        if (isPrimitive) {
+            elementClassID = in.readByte();
+            bytesRead++;
+        } else {
+            elementClassID = readID();
+            bytesRead += identifierSize;
+        }
+
+        // Check for primitive arrays:
+        byte primitiveSignature = 0x00;
+        int elSize = 0;
+        if (isPrimitive || version < VERSION_JDK12BETA4) {
+            switch ((int)elementClassID) {
+                case T_BOOLEAN: {
+                    primitiveSignature = (byte) 'Z';
+                    elSize = 1;
+                    break;
+                }
+                case T_CHAR: {
+                    primitiveSignature = (byte) 'C';
+                    elSize = 2;
+                    break;
+                }
+                case T_FLOAT: {
+                    primitiveSignature = (byte) 'F';
+                    elSize = 4;
+                    break;
+                }
+                case T_DOUBLE: {
+                    primitiveSignature = (byte) 'D';
+                    elSize = 8;
+                    break;
+                }
+                case T_BYTE: {
+                    primitiveSignature = (byte) 'B';
+                    elSize = 1;
+                    break;
+                }
+                case T_SHORT: {
+                    primitiveSignature = (byte) 'S';
+                    elSize = 2;
+                    break;
+                }
+                case T_INT: {
+                    primitiveSignature = (byte) 'I';
+                    elSize = 4;
+                    break;
+                }
+                case T_LONG: {
+                    primitiveSignature = (byte) 'J';
+                    elSize = 8;
+                    break;
+                }
+            }
+            if (version >= VERSION_JDK12BETA4 && primitiveSignature == 0x00) {
+                throw new IOException("Unrecognized typecode:  "
+                                        + elementClassID);
+            }
+        }
+        if (primitiveSignature != 0x00) {
+            int size = elSize * num;
+            bytesRead += size;
+            JavaValueArray va = new JavaValueArray(primitiveSignature, start);
+            skipBytes(size);
+            snapshot.addHeapObject(id, va);
+            snapshot.setSiteTrace(va, stackTrace);
+        } else {
+            int sz = num * identifierSize;
+            bytesRead += sz;
+            JavaObjectArray arr = new JavaObjectArray(elementClassID, start);
+            skipBytes(sz);
+            snapshot.addHeapObject(id, arr);
+            snapshot.setSiteTrace(arr, stackTrace);
+        }
+        return bytesRead;
+    }
+
+    private byte signatureFromTypeId(byte typeId) throws IOException {
+        switch (typeId) {
+            case T_CLASS: {
+                return (byte) 'L';
+            }
+            case T_BOOLEAN: {
+                return (byte) 'Z';
+            }
+            case T_CHAR: {
+                return (byte) 'C';
+            }
+            case T_FLOAT: {
+                return (byte) 'F';
+            }
+            case T_DOUBLE: {
+                return (byte) 'D';
+            }
+            case T_BYTE: {
+                return (byte) 'B';
+            }
+            case T_SHORT: {
+                return (byte) 'S';
+            }
+            case T_INT: {
+                return (byte) 'I';
+            }
+            case T_LONG: {
+                return (byte) 'J';
+            }
+            default: {
+                throw new IOException("Invalid type id of " + typeId);
+            }
+        }
+    }
+
+    private void handleEOF(EOFException exp, Snapshot snapshot) {
+        if (debugLevel > 0) {
+            exp.printStackTrace();
+        }
+        warn("Unexpected EOF. Will miss information...");
+        // we have EOF, we have to tolerate missing references
+        snapshot.setUnresolvedObjectsOK(true);
+    }
+
+    private void warn(String msg) {
+        System.out.println("WARNING: " + msg);
+    }
+
+    //
+    // A trivial data-holder class for HPROF_GC_ROOT_THREAD_OBJ.
+    //
+    private class ThreadObject {
+
+        long threadId;
+        int stackSeq;
+
+        ThreadObject(long threadId, int stackSeq) {
+            this.threadId = threadId;
+            this.stackSeq = stackSeq;
+        }
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/parser/MappedReadBuffer.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,136 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.parser;
+
+import java.io.IOException;
+import java.io.RandomAccessFile;
+import java.nio.MappedByteBuffer;
+import java.nio.channels.FileChannel;
+
+/**
+ * Implementation of ReadBuffer using mapped file buffer
+ *
+ * @author A. Sundararajan
+ */
+class MappedReadBuffer implements ReadBuffer {
+    private MappedByteBuffer buf;
+    private RandomAccessFile file;
+
+    MappedReadBuffer(RandomAccessFile file, MappedByteBuffer buf) {
+        this.file = file;
+        this.buf = buf;
+    }
+
+    /**
+     * Factory method to create correct ReadBuffer for a given file.
+     *
+     * The initial purpose of this method was to choose how to read hprof file for parsing
+     * depending on the size of the file and the system property 'jhat.disableFileMap':
+     * "If file size is more than 2 GB and when file mapping is configured (default),
+     * use mapped file reader".
+     *
+     * However, it has been discovered a problem with this approach.
+     * Creating java.nio.MappedByteBuffer from inside the test leads to hprof file
+     * is locked on Windows until test process dies since there is no good way to
+     * release this resource.
+     *
+     * java.nio.MappedByteBuffer will be used only if 'jhat.enableFileMap' is set to true.
+     * Per default 'jhat.enableFileMap' is not set.
+     */
+    static ReadBuffer create(RandomAccessFile file) throws IOException {
+        if (canUseFileMap()) {
+            MappedByteBuffer buf;
+            try {
+                FileChannel ch = file.getChannel();
+                long size = ch.size();
+                buf = ch.map(FileChannel.MapMode.READ_ONLY, 0, size);
+                ch.close();
+                return new MappedReadBuffer(file, buf);
+            } catch (IOException exp) {
+                exp.printStackTrace();
+                System.err.println("File mapping failed, will use direct read");
+                // fall through
+            }
+        } // else fall through
+        return new FileReadBuffer(file);
+    }
+
+    /**
+     * Set system property 'jhat.enableFileMap' to 'true' to enable file mapping.
+     */
+    private static boolean canUseFileMap() {
+        String prop = System.getProperty("jhat.enableFileMap");
+        return prop != null && prop.equals("true");
+    }
+
+    private void seek(long pos) throws IOException {
+        assert pos <= Integer.MAX_VALUE :  "position overflow";
+        buf.position((int)pos);
+    }
+
+    public synchronized void get(long pos, byte[] res) throws IOException {
+        seek(pos);
+        buf.get(res);
+    }
+
+    public synchronized char getChar(long pos) throws IOException {
+        seek(pos);
+        return buf.getChar();
+    }
+
+    public synchronized byte getByte(long pos) throws IOException {
+        seek(pos);
+        return buf.get();
+    }
+
+    public synchronized short getShort(long pos) throws IOException {
+        seek(pos);
+        return buf.getShort();
+    }
+
+    public synchronized int getInt(long pos) throws IOException {
+        seek(pos);
+        return buf.getInt();
+    }
+
+    public synchronized long getLong(long pos) throws IOException {
+        seek(pos);
+        return buf.getLong();
+    }
+
+    @Override
+    public void close() throws Exception {
+        file.close();
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/parser/PositionDataInputStream.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,64 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.parser;
+
+import java.io.DataInputStream;
+import java.io.InputStream;
+
+/**
+ * A DataInputStream that keeps track of total bytes read
+ * (in effect 'position' in stream) so far.
+ *
+ */
+public class PositionDataInputStream extends DataInputStream {
+    public PositionDataInputStream(InputStream in) {
+        super(in instanceof PositionInputStream?
+              in : new PositionInputStream(in));
+    }
+
+    public boolean markSupported() {
+        return false;
+    }
+
+    public void mark(int readLimit) {
+        throw new UnsupportedOperationException("mark");
+    }
+
+    public void reset() {
+        throw new UnsupportedOperationException("reset");
+    }
+
+    public long position() {
+        return ((PositionInputStream)in).position();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/parser/PositionInputStream.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,84 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.parser;
+
+import java.io.FilterInputStream;
+import java.io.IOException;
+import java.io.InputStream;
+
+/**
+ * InputStream that keeps track of total bytes read (in effect
+ * 'position' in stream) from the input stream.
+ *
+ */
+public class PositionInputStream extends FilterInputStream {
+    private long position = 0L;
+
+    public PositionInputStream(InputStream in) {
+        super(in);
+    }
+
+    public int read() throws IOException {
+        int res = super.read();
+        if (res != -1) position++;
+        return res;
+    }
+
+    public int read(byte[] b, int off, int len) throws IOException {
+        int res = super.read(b, off, len);
+        if (res != -1) position += res;
+        return res;
+    }
+
+    public long skip(long n) throws IOException {
+        long res = super.skip(n);
+        position += res;
+        return res;
+    }
+
+    public boolean markSupported() {
+        return false;
+    }
+
+    public void mark(int readLimit) {
+        throw new UnsupportedOperationException("mark");
+    }
+
+    public void reset() {
+        throw new UnsupportedOperationException("reset");
+    }
+
+    public long position() {
+        return position;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/parser/ReadBuffer.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,51 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.parser;
+
+import java.io.IOException;
+
+/**
+ * Positionable read only buffer
+ *
+ * @author A. Sundararajan
+ */
+public interface ReadBuffer extends AutoCloseable {
+    // read methods - only byte array and int primitive types.
+    // read position has to be specified always.
+    public void  get(long pos, byte[] buf) throws IOException;
+    public char  getChar(long pos) throws IOException;
+    public byte  getByte(long pos) throws IOException;
+    public short getShort(long pos) throws IOException;
+    public int   getInt(long pos) throws IOException;
+    public long  getLong(long pos) throws IOException;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/parser/Reader.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,97 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.parser;
+
+import java.io.*;
+import jdk.test.lib.hprof.model.*;
+
+/**
+ * Abstract base class for reading object dump files.  A reader need not be
+ * thread-safe.
+ *
+ * @author      Bill Foote
+ */
+
+
+public abstract class Reader {
+    protected PositionDataInputStream in;
+
+    protected Reader(PositionDataInputStream in) {
+        this.in = in;
+    }
+
+    /**
+     * Read a snapshot from a data input stream.  It is assumed that the magic
+     * number has already been read.
+     */
+    abstract public Snapshot read() throws IOException;
+
+    /**
+     * Read a snapshot from a file.
+     *
+     * @param heapFile The name of a file containing a heap dump
+     * @param callStack If true, read the call stack of allocaation sites
+     */
+    public static Snapshot readFile(String heapFile, boolean callStack,
+                                    int debugLevel)
+            throws IOException {
+        int dumpNumber = 1;
+        int pos = heapFile.lastIndexOf('#');
+        if (pos > -1) {
+            String num = heapFile.substring(pos+1, heapFile.length());
+            try {
+                dumpNumber = Integer.parseInt(num, 10);
+            } catch (java.lang.NumberFormatException ex) {
+                String msg = "In file name \"" + heapFile
+                             + "\", a dump number was "
+                             + "expected after the :, but \""
+                             + num + "\" was found instead.";
+                System.err.println(msg);
+                throw new IOException(msg);
+            }
+            heapFile = heapFile.substring(0, pos);
+        }
+        try (PositionDataInputStream in = new PositionDataInputStream(
+                new BufferedInputStream(new FileInputStream(heapFile)))) {
+            int i = in.readInt();
+            if (i == HprofReader.MAGIC_NUMBER) {
+                Reader r
+                    = new HprofReader(heapFile, in, dumpNumber,
+                                      callStack, debugLevel);
+                return r.read();
+            } else {
+                throw new IOException("Unrecognized magic number: " + i);
+            }
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/util/ArraySorter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,147 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.util;
+import java.util.*;
+
+/**
+ * A singleton utility class that sorts an array of objects.
+ * <p>
+ * Use:
+ * <pre>
+ *
+ *  Stuff[] arr = ...;
+ *  ArraySorter.sort(arr, new Comparer() {
+ *      public int compare(Object lhs, Object rhs) {
+ *          return ((String) lhs).compareTo((String) rhs);
+ *      }
+ *  });
+ * </pre>
+ *
+ * @author      Bill Foote
+ */
+
+public class ArraySorter {
+
+    /**
+     * Sort the given array, using c for comparison
+    **/
+    static public void sort(Object[] arr, Comparer c)  {
+        quickSort(arr, c, 0, arr.length-1);
+    }
+
+
+    /**
+     * Sort an array of strings, using String.compareTo()
+    **/
+    static public void sortArrayOfStrings(Object[] arr) {
+        sort(arr, new Comparer() {
+            public int compare(Object lhs, Object rhs) {
+                return ((String) lhs).compareTo((String) rhs);
+            }
+        });
+    }
+
+
+    static private void swap(Object[] arr, int a, int b) {
+        Object tmp = arr[a];
+        arr[a] = arr[b];
+        arr[b] = tmp;
+    }
+
+    //
+    // Sorts arr between from and to, inclusive.  This is a quick, off-the-top-
+    // of-my-head quicksort:  I haven't put any thought into optimizing it.
+    // I _did_ put thought into making sure it's safe (it will always
+    // terminate).  Worst-case it's O(n^2), but it will usually run in
+    // in O(n log n).  It's well-behaved if the list is already sorted,
+    // or nearly so.
+    //
+    static private void quickSort(Object[] arr, Comparer c, int from, int to) {
+        if (to <= from)
+            return;
+        int mid = (from + to) / 2;
+        if (mid != from)
+            swap(arr, mid, from);
+        Object pivot = arr[from];   // Simple-minded, but reasonable
+        int highestBelowPivot = from - 1;
+        int low = from+1;
+        int high = to;
+            // We now move low and high toward each other, maintaining the
+            // invariants:
+            //      arr[i] <= pivot    for all i < low
+            //      arr[i] > pivot     for all i > high
+            // As long as these invariants hold, and every iteration makes
+            // progress, we are safe.
+        while (low <= high) {
+            int cmp = c.compare(arr[low], pivot);
+            if (cmp <= 0) {   // arr[low] <= pivot
+                if (cmp < 0) {
+                    highestBelowPivot = low;
+                }
+                low++;
+            } else {
+                int c2;
+                for (;;) {
+                        // arr[high] > pivot:
+                    c2 = c.compare(arr[high], pivot);
+                    if (c2 > 0) {
+                        high--;
+                        if (low > high) {
+                            break;
+                        }
+                    } else {
+                        break;
+                    }
+                }
+                // At this point, low is never == high, BTW
+                if (low <= high) {
+                    swap(arr, low, high);
+                    if (c2 < 0) {
+                        highestBelowPivot = low;
+                    }
+                    low++;
+                    high--;
+                }
+            }
+        }
+        // At this point, low == high+1
+        // Now we just need to sort from from..highestBelowPivot
+        // and from high+1..to
+        if (highestBelowPivot > from) {
+            // pivot == pivot, so ensure algorithm terminates
+            swap(arr, from, highestBelowPivot);
+            quickSort(arr, c, from, highestBelowPivot-1);
+        }
+        quickSort(arr, c, high+1, to);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/util/Comparer.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,49 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.util;
+
+/**
+ * Base class for comparison of two objects.
+ * @see VectorSorter
+ *
+ * @author      Bill Foote
+ */
+
+abstract public class Comparer {
+
+    /**
+     * @return a number <, == or > 0 depending on lhs compared to rhs
+     * @see java.lang.String.compareTo
+    **/
+    abstract public int compare(Object lhs, Object rhs);
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/util/CompositeEnumeration.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,63 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.util;
+
+import java.util.Enumeration;
+import java.util.NoSuchElementException;
+import jdk.test.lib.hprof.model.JavaHeapObject;
+
+public class CompositeEnumeration implements Enumeration<JavaHeapObject> {
+    Enumeration<JavaHeapObject> e1;
+    Enumeration<JavaHeapObject> e2;
+
+    public CompositeEnumeration(Enumeration<JavaHeapObject> e1, Enumeration<JavaHeapObject> e2) {
+        this.e1 = e1;
+        this.e2 = e2;
+    }
+
+    public boolean hasMoreElements() {
+        return e1.hasMoreElements() || e2.hasMoreElements();
+    }
+
+    public JavaHeapObject nextElement() {
+        if (e1.hasMoreElements()) {
+            return e1.nextElement();
+        }
+
+        if (e2.hasMoreElements()) {
+            return e2.nextElement();
+        }
+
+        throw new NoSuchElementException();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/util/Misc.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,112 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.util;
+import java.util.*;
+
+/**
+ * Miscellaneous functions I couldn't think of a good place to put.
+ *
+ * @author      Bill Foote
+ */
+
+
+public class Misc {
+
+    private static char[] digits = { '0', '1', '2', '3', '4', '5', '6', '7',
+                                     '8', '9', 'a', 'b', 'c', 'd', 'e', 'f' };
+
+    public final static String toHex(int addr) {
+        char[] buf = new char[8];
+        int i = 0;
+        for (int s = 28; s >= 0; s -= 4) {
+            buf[i++] = digits[(addr >> s) & 0xf];
+        }
+        return "0x" + new String(buf);
+    }
+
+    public final static String toHex(long addr) {
+        return "0x" + Long.toHexString(addr);
+    }
+
+    public final static long parseHex(String value) {
+        long result = 0;
+        if (value.length() < 2 || value.charAt(0) != '0' ||
+            value.charAt(1) != 'x') {
+            return -1L;
+        }
+        for(int i = 2; i < value.length(); i++) {
+            result *= 16;
+            char ch = value.charAt(i);
+            if (ch >= '0' && ch <= '9') {
+                result += (ch - '0');
+            } else if (ch >= 'a' && ch <= 'f') {
+                result += (ch - 'a') + 10;
+            } else if (ch >= 'A' && ch <= 'F') {
+                result += (ch - 'A') + 10;
+            } else {
+                throw new NumberFormatException("" + ch
+                                        + " is not a valid hex digit");
+            }
+        }
+        return result;
+    }
+
+    public static String encodeHtml(String str) {
+        final int len = str.length();
+        StringBuilder sb = new StringBuilder();
+        for (int i = 0; i < len; i++) {
+            char ch = str.charAt(i);
+            if (ch == '<') {
+                sb.append("&lt;");
+            } else if (ch == '>') {
+                sb.append("&gt;");
+            } else if (ch == '"') {
+                sb.append("&quot;");
+            } else if (ch == '\'') {
+                sb.append("&#039;");
+            } else if (ch == '&') {
+                sb.append("&amp;");
+            } else if (ch < ' ') {
+                sb.append("&#").append((int)ch).append(';');
+            } else {
+                int c = (ch & 0xFFFF);
+                if (c > 127) {
+                    sb.append("&#").append(c).append(';');
+                } else {
+                    sb.append(ch);
+                }
+            }
+        }
+        return sb.toString();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/lib/share/classes/jdk/test/lib/hprof/util/VectorSorter.java	Wed Jul 05 20:35:10 2017 +0200
@@ -0,0 +1,148 @@
+/*
+ * 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
+ * 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.
+ */
+
+
+/*
+ * The Original Code is HAT. The Initial Developer of the
+ * Original Code is Bill Foote, with contributions from others
+ * at JavaSoft/Sun.
+ */
+
+package jdk.test.lib.hprof.util;
+import java.util.*;
+
+/**
+ * A singleton utility class that sorts a vector.
+ * <p>
+ * Use:
+ * <pre>
+ *
+ *  Vector v =   <a vector of, say, String objects>;
+ *  VectorSorter.sort(v, new Comparer() {
+ *      public int compare(Object lhs, Object rhs) {
+ *          return ((String) lhs).compareTo((String) rhs);
+ *      }
+ *  });
+ * </pre>
+ *
+ * @author      Bill Foote
+ */
+
+
+public class VectorSorter {
+
+    /**
+     * Sort the given vector, using c for comparison
+    **/
+    static public void sort(Vector<Object> v, Comparer c)  {
+        quickSort(v, c, 0, v.size()-1);
+    }
+
+
+    /**
+     * Sort a vector of strings, using String.compareTo()
+    **/
+    static public void sortVectorOfStrings(Vector<Object> v) {
+        sort(v, new Comparer() {
+            public int compare(Object lhs, Object rhs) {
+                return ((String) lhs).compareTo((String) rhs);
+            }
+        });
+    }
+
+
+    static private void swap(Vector<Object> v, int a, int b) {
+        Object tmp = v.elementAt(a);
+        v.setElementAt(v.elementAt(b), a);
+        v.setElementAt(tmp, b);
+    }
+
+    //
+    // Sorts v between from and to, inclusive.  This is a quick, off-the-top-
+    // of-my-head quicksort:  I haven't put any thought into optimizing it.
+    // I _did_ put thought into making sure it's safe (it will always
+    // terminate).  Worst-case it's O(n^2), but it will usually run in
+    // in O(n log n).  It's well-behaved if the list is already sorted,
+    // or nearly so.
+    //
+    static private void quickSort(Vector<Object> v, Comparer c, int from, int to) {
+        if (to <= from)
+            return;
+        int mid = (from + to) / 2;
+        if (mid != from)
+            swap(v, mid, from);
+        Object pivot = v.elementAt(from);
+                        // Simple-minded, but reasonable
+        int highestBelowPivot = from - 1;
+        int low = from+1;
+        int high = to;
+            // We now move low and high toward eachother, maintaining the
+            // invariants:
+            //      v[i] <= pivot    for all i < low
+            //      v[i] > pivot     for all i > high
+            // As long as these invariants hold, and every iteration makes
+            // progress, we are safe.
+        while (low <= high) {
+            int cmp = c.compare(v.elementAt(low), pivot);
+            if (cmp <= 0) {    // v[low] <= pivot
+                if (cmp < 0) {
+                    highestBelowPivot = low;
+                }
+                low++;
+            } else {
+                int c2;
+                for (;;) {
+                    c2 = c.compare(v.elementAt(high), pivot);
+                        // v[high] > pivot:
+                    if (c2 > 0) {
+                        high--;
+                        if (low > high) {
+                            break;
+                        }
+                    } else {
+                        break;
+                    }
+                }
+                // At this point, low is never == high
+                if (low <= high) {
+                    swap(v, low, high);
+                    if (c2 < 0) {
+                        highestBelowPivot = low;
+                    }
+                    low++;
+                    high--;
+                }
+            }
+        }
+        // Now we just need to sort from from..highestBelowPivot
+        // and from high+1..to
+        if (highestBelowPivot > from) {
+            // pivot == pivot, so ensure algorithm terminates
+            swap(v, from, highestBelowPivot);
+            quickSort(v, c, from, highestBelowPivot-1);
+        }
+        quickSort(v, c, high+1, to);
+    }
+}