changeset 23974:f13e777eb255

Merge with jdk8u111-b14
author Tom Rodriguez <tom.rodriguez@oracle.com>
date Wed, 16 Nov 2016 12:32:54 -0800
parents 3953f8820df8 (current diff) e42acc0165ef (diff)
children ac36c0370367
files .hgtags agent/src/os/linux/symtab.c make/windows/makefiles/sa.make src/cpu/sparc/vm/c1_LIRAssembler_sparc.cpp src/cpu/sparc/vm/vm_version_sparc.cpp src/cpu/sparc/vm/vm_version_sparc.hpp src/cpu/x86/vm/assembler_x86.cpp src/cpu/x86/vm/assembler_x86.hpp src/cpu/x86/vm/c1_LIRAssembler_x86.cpp src/cpu/x86/vm/c1_LIRGenerator_x86.cpp src/cpu/x86/vm/macroAssembler_x86.cpp src/cpu/x86/vm/macroAssembler_x86.hpp src/cpu/x86/vm/sharedRuntime_x86_64.cpp src/cpu/x86/vm/stubGenerator_x86_64.cpp src/cpu/x86/vm/vm_version_x86.cpp src/os/linux/vm/os_linux.cpp src/os/posix/vm/os_posix.cpp src/os/solaris/vm/os_solaris.cpp src/os_cpu/solaris_sparc/vm/vm_version_solaris_sparc.cpp src/share/vm/c1/c1_Canonicalizer.cpp src/share/vm/c1/c1_GraphBuilder.cpp src/share/vm/c1/c1_LIRGenerator.cpp src/share/vm/c1/c1_Runtime1.cpp src/share/vm/ci/ciObjectFactory.cpp src/share/vm/classfile/classFileParser.cpp src/share/vm/classfile/dictionary.cpp src/share/vm/classfile/javaClasses.cpp src/share/vm/classfile/javaClasses.hpp src/share/vm/classfile/systemDictionary.cpp src/share/vm/classfile/verifier.cpp src/share/vm/classfile/vmSymbols.hpp src/share/vm/compiler/oopMap.hpp src/share/vm/gc_implementation/concurrentMarkSweep/concurrentMarkSweepGeneration.cpp src/share/vm/gc_implementation/g1/g1CollectedHeap.cpp src/share/vm/gc_implementation/g1/heapRegion.cpp src/share/vm/gc_implementation/g1/heapRegionRemSet.cpp src/share/vm/gc_implementation/g1/heapRegionRemSet.hpp src/share/vm/gc_implementation/shared/adaptiveSizePolicy.cpp src/share/vm/interpreter/templateInterpreter.cpp src/share/vm/memory/allocation.cpp src/share/vm/memory/metaspaceShared.cpp src/share/vm/memory/universe.cpp src/share/vm/oops/instanceKlass.cpp src/share/vm/oops/klassVtable.cpp src/share/vm/oops/method.cpp src/share/vm/oops/method.hpp src/share/vm/opto/c2_globals.hpp src/share/vm/opto/c2compiler.cpp src/share/vm/opto/c2compiler.hpp src/share/vm/opto/callGenerator.cpp src/share/vm/opto/cfgnode.cpp src/share/vm/opto/compile.cpp src/share/vm/opto/compile.hpp src/share/vm/opto/connode.cpp src/share/vm/opto/connode.hpp src/share/vm/opto/escape.cpp src/share/vm/opto/generateOptoStub.cpp src/share/vm/opto/graphKit.cpp src/share/vm/opto/graphKit.hpp src/share/vm/opto/lcm.cpp src/share/vm/opto/library_call.cpp src/share/vm/opto/loopTransform.cpp src/share/vm/opto/loopnode.hpp src/share/vm/opto/loopopts.cpp src/share/vm/opto/macro.cpp src/share/vm/opto/node.cpp src/share/vm/opto/node.hpp src/share/vm/opto/parse1.cpp src/share/vm/opto/parse2.cpp src/share/vm/opto/phaseX.cpp src/share/vm/opto/runtime.cpp src/share/vm/opto/stringopts.cpp src/share/vm/opto/superword.cpp src/share/vm/opto/type.cpp src/share/vm/opto/type.hpp src/share/vm/prims/jni.cpp src/share/vm/prims/jvm.cpp src/share/vm/prims/jvmtiEnter.xsl src/share/vm/prims/jvmtiEnv.cpp src/share/vm/prims/jvmtiEnvBase.cpp src/share/vm/prims/jvmtiExport.cpp src/share/vm/prims/jvmtiRedefineClasses.cpp src/share/vm/prims/unsafe.cpp src/share/vm/prims/whitebox.cpp src/share/vm/runtime/arguments.cpp src/share/vm/runtime/deoptimization.cpp src/share/vm/runtime/globals.hpp src/share/vm/runtime/java.cpp src/share/vm/runtime/os.cpp src/share/vm/runtime/safepoint.cpp src/share/vm/runtime/sharedRuntime.cpp src/share/vm/runtime/sharedRuntime.hpp src/share/vm/runtime/signature.cpp src/share/vm/runtime/stubRoutines.cpp src/share/vm/runtime/stubRoutines.hpp src/share/vm/runtime/thread.cpp src/share/vm/runtime/vmStructs.cpp src/share/vm/runtime/vm_version.hpp src/share/vm/services/diagnosticCommand.cpp src/share/vm/services/diagnosticCommand.hpp src/share/vm/services/heapDumper.cpp src/share/vm/services/threadService.hpp test/TEST.groups test/gc/8000311/Test8000311.java test/gc/TestG1ZeroPGCTJcmdThreadPrint.java
diffstat 138 files changed, 4191 insertions(+), 587 deletions(-) [+]
line wrap: on
line diff
--- a/.hgtags	Wed Nov 09 14:41:57 2016 -0800
+++ b/.hgtags	Wed Nov 16 12:32:54 2016 -0800
@@ -598,6 +598,7 @@
 6824e2475e0432e27f9cc51838bc34ea5fbf5113 jdk8u40-b27
 8220f68a195f6eeed2f5fb6e8a303726b512e899 jdk8u40-b31
 850a290eb1088a61178d1910c500e170ef4f4386 jdk8u40-b32
+e6aa4a8c1b46a05b6c493b4ffe5c2555013f5c99 jdk8u40-b33
 1b3abbeee961dee49780c0e4af5337feb918c555 jdk8u40-b10
 f10fe402dfb1543723b4b117a7cba3ea3d4159f1 hs25.40-b15
 99372b2fee0eb8b3452f47230e84aa6e97003184 jdk8u40-b11
@@ -801,17 +802,28 @@
 a8e4754b89aecc388623394a20f6d43d4c58f083 jdk8u72-b13
 dc2fdd4e0b8105268b8231040f761f27ab4523f2 jdk8u72-b14
 d6670c5d49ba381405ec9f69a78ccc5b8b0c8473 jdk8u72-b15
+da43260704c28b9f19cb652090ae65c258220fd6 jdk8u72-b31
 26b99cd20661a1fa05939d1856a9389311e01c4f jdk8u73-b00
 931c31db01ae873525a1b2c306b01129eb431960 jdk8u73-b01
 67566d815a66d958c1f817d65f1621ba1d2e5f33 jdk8u73-b02
 451dda77f6c29bd3260e87f847a9eadae122a759 jdk8u74-b00
 c1031a924f2c910fad078838b88a2f0146f2de98 jdk8u74-b01
 ca9cae9aa9e989bbe6713c91d55c913edeaecce4 jdk8u74-b02
+a5b78b56841e97ce00463874f1b7f63c54d84934 jdk8u74-b31
+94ec11846b18111e73929b6caa9fbe7262e142c1 jdk8u74-b32
+1b6d4fd2730e58f17820930f797938dc182117c4 jdk8u77-b00
+ddd297e340b1170d3cec011ee64e729f8b493c86 jdk8u77-b01
+1b4072e4bb3ad54c4e894998486a8b33f0689160 jdk8u77-b02
+223b64a19e94222dd97b92bb40abcfbc0bf6ef1f jdk8u77-b03
+dd8507f51d786572dae18af8ffdc5a1ea34c755e jdk8u77-b31
+
+94ec11846b18111e73929b6caa9fbe7262e142c1 jdk8u74-b32
 da43260704c28b9f19cb652090ae65c258220fd6 jdk8u72-b31
 c0242ea4bde19d72be5149feda112a39e8c89b0a jdk8u75-b00
 ca3b8c8e390ab0540b0cc2e5def869b38e460d86 jdk8u75-b01
 9aef5b5e0a68f20059cfa9e2806b4ff0e11a3d31 jdk8u75-b02
 2df9fe896819362b9075a670b78106b249e50d6d jdk8u75-b03
+b374548dcb4834eb8731a06b52faddd0f10bd45d jdk8u101-b00
 32b682649973231b54740c09b10889660f6ebde5 jdk8u75-b04
 1f43bd4fab06d2ca5d1964611df14d8506d6b36e jdk8u75-b05
 916712f178c39d0acbc590f38802133fc86a7346 jdk8u75-b06
@@ -827,6 +839,11 @@
 bbbb05e91c629f8d9eef2ba43933767f68a898b0 jdk8u91-b00
 e36b6ade0499eadfd8673fe62ef0a613af2e6d67 jdk8u91-b13
 fa8991ccf6e5b74890a0b5672440b3c09d8d8732 jdk8u91-b14
+e1ea97ad19af4d1e0bda449aa43be7e1b118ffe9 jdk8u91-b15
+1b6d4fd2730e58f17820930f797938dc182117c4 jdk8u77-b00
+ddd297e340b1170d3cec011ee64e729f8b493c86 jdk8u77-b01
+1b4072e4bb3ad54c4e894998486a8b33f0689160 jdk8u77-b02
+223b64a19e94222dd97b92bb40abcfbc0bf6ef1f jdk8u77-b03
 d7b01fb81aa8a5437cb03bc36afe15cf0e55fb89 jdk8u76-b00
 c1679cc87ba045219169cabb6b9b378c2b5cc578 jdk8u76-b01
 218483967e52b419d885d34af4488a81c5133804 jdk8u76-b02
@@ -842,6 +859,57 @@
 9a87701e22b3cae79fdfd8cdb732051e02a710fa jdk8u76-b12
 481dcde745b6aec035781ed9f6797cfc93719f71 jdk8u92-b00
 f3e1e734e2d29101a9537ddeb71ecad413fcd352 jdk8u92-b13
+24a09407d71bb2cc4848bfa21660c890b4d722b1 jdk8u92-b14
+445941ba41c0e3829fe02140690b144281ac2141 jdk8u92-b31
+f958bebdee267695e37aadd27753ac8b1e1823c8 jdk8u92-b32
+d1bb0e79ff79d21068388d9c62ca01e3c072fd0d jdk8u92-b33
+d0388be32561e4bd00c1a79adbe301cfdd6ba9f2 jdk8u92-b34
+b374548dcb4834eb8731a06b52faddd0f10bd45d jdk8u81-b00
+ead07188d11107e877e8e4ad215ff6cb238a8a92 jdk8u101-b01
+34429bad9986677f4991c80aeb22665842881cba jdk8u101-b02
+b41d5faaf1d32ed1bf9592f65f2f94ddd4c60fc4 jdk8u101-b03
+ceecf88e5c2c09bfabf5926581e6d0b0f65f5148 jdk8u101-b04
+19e74265fc8def6a7fc96c836d8ebe38ad1cf199 jdk8u101-b05
+7c60503b0888ac16eac80a6cd074195973f8dedb jdk8u101-b06
+cb4af293fe70549b51039bb9197f373e6750fafb jdk8u101-b07
+8ed377d2cec94435d1617a37999960a24be73ad9 jdk8u101-b08
+9be452c4e7161e60d623d55bb72ad013386aefd1 jdk8u101-b09
+218a44a163fa8c2532fd5f2e8ea9bc3c9c2ca8cf jdk8u101-b10
+0095e54dcaa1acfe1614feff9600734c26af7ae8 jdk8u101-b11
+286fe17d81c3d153611a28e50926083ae934cc56 jdk8u101-b12
+77df35b662ed98236f67ab18e23691460f986981 jdk8u101-b13
+d6c92b9e192ef97305a699e868387d55821c81ad jdk8u102-b00
+d6c92b9e192ef97305a699e868387d55821c81ad jdk8u82-b00
+516a64e6d7c2dc29fd932bf3b8313e560a01bcd0 jdk8u102-b01
+83dc7e55f71596e6e76fabfa56b6008e070ff44c jdk8u102-b02
+ef01a1634bb41dd5b36fc9824f8d35f745c6bd5a jdk8u102-b03
+2094cac55c5955b4f19cd9e35e3be8b467e59b57 jdk8u102-b04
+a96cf90239c64f51679d106b852c9a5b343b9488 jdk8u102-b05
+12cd1f9b403eb5024e8642bfa59136cd275899a4 jdk8u102-b06
+9ff5455815c1864ef7ca2d5232decd2023d1d043 jdk8u102-b07
+69f5f6c2beeb3bb126494ed779ae1686f61602b9 jdk8u102-b08
+b5ecd8067e899c4bfb8d327ee7583a32129772d4 jdk8u102-b09
+2672cfc2d7b6ffa07b7714208f9d46a405211d94 jdk8u102-b10
+36a1a2875ed55fa17818f3eb203e27922a7b4589 jdk8u102-b11
+340e1a736ef7169786e70db7f31ffd32bc3be24d jdk8u102-b12
+f6daf04c0f48dab5420ad63d21da82a7fa4e3ad7 jdk8u102-b13
+ac29c9c1193aef5d480b200ed94c5d579243c17b jdk8u102-b14
+96e1c72fc617d3c6c125bcfc9182f77fc6aa38e6 jdk8u102-b31
+ceecf88e5c2c09bfabf5926581e6d0b0f65f5148 jdk8u111-b00
+e73d79ce00e4a0451e464c7a73d9c911d01e169a jdk8u111-b01
+d584a614818562e1187e1a15c202aec01491caeb jdk8u111-b02
+a3ede966ecfe6009fe4a58fbd6903c470a059ad3 jdk8u111-b03
+65029655928a834018a6793253c9b2699044af92 jdk8u111-b04
+e4525db272634b980738003eff99ac1588bb79d3 jdk8u111-b05
+019b22dd8128840ecdcd1bfebcf4447e28e45068 jdk8u111-b06
+3f337aaf090769653ee0a746fbe661d09055a883 jdk8u111-b07
+e180e364a40364a059a20c74b97ab4e928e2b676 jdk8u111-b08
+c48b303692bb86c42e928da6dec815e901a24c5b jdk8u111-b09
+96973081eb8a132ca3bfee9249ad99c185b6b130 jdk8u111-b10
+603804f2132ff188a9f3d1c31cca63b47220e2e2 jdk8u111-b11
+055bc2a065a503e8714ff7ad27e6197dc0339efa jdk8u111-b12
+c3b42c43c230f10e79ae850ee9062fe86d3c75c9 jdk8u111-b13
+05a6a5823aa58a0a4720a328a9db484f21d573bc jdk8u111-b14
 b124e22eb772806c13d942cc110de38da0108147 graal-0.1
 483d05bf77a7c2a762aca1e06c4191bc06647176 graal-0.2
 9535eccd2a115f6c6f0b15efb508b11ff74cc0d3 graal-0.3
--- a/agent/src/os/linux/symtab.c	Wed Nov 09 14:41:57 2016 -0800
+++ b/agent/src/os/linux/symtab.c	Wed Nov 16 12:32:54 2016 -0800
@@ -514,6 +514,7 @@
      return (uintptr_t)NULL;
 
   item.key = (char*) strdup(sym_name);
+  item.data = NULL;
   hsearch_r(item, FIND, &ret, symtab->hash_table);
   if (ret) {
     struct elf_symbol * sym = (struct elf_symbol *)(ret->data);
--- a/agent/src/share/classes/sun/jvm/hotspot/oops/OopUtilities.java	Wed Nov 09 14:41:57 2016 -0800
+++ b/agent/src/share/classes/sun/jvm/hotspot/oops/OopUtilities.java	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -219,7 +219,7 @@
     if (threadNameField == null) {
       SystemDictionary sysDict = VM.getVM().getSystemDictionary();
       InstanceKlass k = sysDict.getThreadKlass();
-      threadNameField  = (OopField) k.findField("name", "[C");
+      threadNameField  = (OopField) k.findField("name", "Ljava/lang/String;");
       threadGroupField = (OopField) k.findField("group", "Ljava/lang/ThreadGroup;");
       threadEETopField = (LongField) k.findField("eetop", "J");
       threadTIDField = (LongField) k.findField("tid", "J");
@@ -258,7 +258,7 @@
 
   public static String threadOopGetName(Oop threadOop) {
     initThreadFields();
-    return charArrayToString((TypeArray) threadNameField.getValue(threadOop));
+    return stringOopToString(threadNameField.getValue(threadOop));
   }
 
   /** May return null if, e.g., thread was not started */
--- a/make/windows/makefiles/sa.make	Wed Nov 09 14:41:57 2016 -0800
+++ b/make/windows/makefiles/sa.make	Wed Nov 16 12:32:54 2016 -0800
@@ -44,9 +44,11 @@
 HS_ALT_SRC_REL=src/closed
 HS_ALT_SRC = $(WorkSpace)/$(HS_ALT_SRC_REL)
 !ifndef HS_ALT_MAKE
+!if exist($(WorkSpace)/make/closed)
 HS_ALT_MAKE=$(WorkSpace)/make/closed
 !endif
 !endif
+!endif
 
 HS_COMMON_SRC = $(WorkSpace)/$(HS_COMMON_SRC_REL)
 
--- a/src/cpu/sparc/vm/c1_LIRAssembler_sparc.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/cpu/sparc/vm/c1_LIRAssembler_sparc.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -2167,6 +2167,27 @@
     __ delayed()->nop();
   }
 
+  // If the compiler was not able to prove that exact type of the source or the destination
+  // of the arraycopy is an array type, check at runtime if the source or the destination is
+  // an instance type.
+  if (flags & LIR_OpArrayCopy::type_check) {
+    if (!(flags & LIR_OpArrayCopy::LIR_OpArrayCopy::dst_objarray)) {
+      __ load_klass(dst, tmp);
+      __ lduw(tmp, in_bytes(Klass::layout_helper_offset()), tmp2);
+      __ cmp(tmp2, Klass::_lh_neutral_value);
+      __ br(Assembler::greaterEqual, false, Assembler::pn, *stub->entry());
+      __ delayed()->nop();
+    }
+
+    if (!(flags & LIR_OpArrayCopy::LIR_OpArrayCopy::src_objarray)) {
+      __ load_klass(src, tmp);
+      __ lduw(tmp, in_bytes(Klass::layout_helper_offset()), tmp2);
+      __ cmp(tmp2, Klass::_lh_neutral_value);
+      __ br(Assembler::greaterEqual, false, Assembler::pn, *stub->entry());
+      __ delayed()->nop();
+    }
+  }
+
   if (flags & LIR_OpArrayCopy::src_pos_positive_check) {
     // test src_pos register
     __ cmp_zero_and_br(Assembler::less, src_pos, *stub->entry());
--- a/src/cpu/sparc/vm/vm_version_sparc.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/cpu/sparc/vm/vm_version_sparc.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -40,7 +40,10 @@
 unsigned int VM_Version::_L2_data_cache_line_size = 0;
 
 void VM_Version::initialize() {
-  _features = determine_features();
+
+  assert(_features != VM_Version::unknown_m, "System pre-initialization is not complete.");
+  guarantee(VM_Version::has_v9(), "only SPARC v9 is supported");
+
   PrefetchCopyIntervalInBytes = prefetch_copy_interval_in_bytes();
   PrefetchScanIntervalInBytes = prefetch_scan_interval_in_bytes();
   PrefetchFieldsAhead         = prefetch_fields_ahead();
@@ -76,8 +79,6 @@
     FLAG_SET_DEFAULT(AllocatePrefetchStyle, 1);
   }
 
-  guarantee(VM_Version::has_v9(), "only SPARC v9 is supported");
-
   assert(ArraycopySrcPrefetchDistance < 4096, "invalid value");
   if (ArraycopySrcPrefetchDistance >= 4096)
     ArraycopySrcPrefetchDistance = 4064;
--- a/src/cpu/sparc/vm/vm_version_sparc.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/cpu/sparc/vm/vm_version_sparc.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -125,6 +125,8 @@
   // Initialization
   static void initialize();
 
+  static void init_before_ergo()        { _features = determine_features(); }
+
   // Instruction support
   static bool has_v8()                  { return (_features & v8_instructions_m) != 0; }
   static bool has_v9()                  { return (_features & v9_instructions_m) != 0; }
--- a/src/cpu/x86/vm/assembler_x86.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/cpu/x86/vm/assembler_x86.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -2359,6 +2359,13 @@
   emit_arith(0x0B, 0xC0, dst, src);
 }
 
+void Assembler::orl(Address dst, Register src) {
+  InstructionMark im(this);
+  prefix(dst, src);
+  emit_int8(0x09);
+  emit_operand(src, dst);
+}
+
 void Assembler::packuswb(XMMRegister dst, Address src) {
   NOT_LP64(assert(VM_Version::supports_sse2(), ""));
   assert((UseAVX > 0), "SSE mode requires address alignment 16 bytes");
@@ -5654,6 +5661,19 @@
   }
 }
 
+void Assembler::rcrq(Register dst, int imm8) {
+  assert(isShiftCount(imm8 >> 1), "illegal shift count");
+  int encode = prefixq_and_encode(dst->encoding());
+  if (imm8 == 1) {
+    emit_int8((unsigned char)0xD1);
+    emit_int8((unsigned char)(0xD8 | encode));
+  } else {
+    emit_int8((unsigned char)0xC1);
+    emit_int8((unsigned char)(0xD8 | encode));
+    emit_int8(imm8);
+  }
+}
+
 void Assembler::rorq(Register dst, int imm8) {
   assert(isShiftCount(imm8 >> 1), "illegal shift count");
   int encode = prefixq_and_encode(dst->encoding());
--- a/src/cpu/x86/vm/assembler_x86.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/cpu/x86/vm/assembler_x86.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1459,6 +1459,7 @@
   void orl(Register dst, int32_t imm32);
   void orl(Register dst, Address src);
   void orl(Register dst, Register src);
+  void orl(Address dst, Register src);
 
   void orq(Address dst, int32_t imm32);
   void orq(Register dst, int32_t imm32);
@@ -1559,6 +1560,8 @@
 
   void rclq(Register dst, int imm8);
 
+  void rcrq(Register dst, int imm8);
+
   void rdtsc();
 
   void ret(int imm16);
--- a/src/cpu/x86/vm/c1_LIRAssembler_x86.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/cpu/x86/vm/c1_LIRAssembler_x86.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1714,8 +1714,8 @@
   Register Rtmp1 = noreg;
 
   // check if it needs to be profiled
-  ciMethodData* md;
-  ciProfileData* data;
+  ciMethodData* md = NULL;
+  ciProfileData* data = NULL;
 
   if (op->should_profile()) {
     ciMethod* method = op->profiled_method();
@@ -1874,8 +1874,8 @@
     CodeStub* stub = op->stub();
 
     // check if it needs to be profiled
-    ciMethodData* md;
-    ciProfileData* data;
+    ciMethodData* md = NULL;
+    ciProfileData* data = NULL;
 
     if (op->should_profile()) {
       ciMethod* method = op->profiled_method();
@@ -2052,7 +2052,8 @@
     case lir_cond_greater:      acond = Assembler::greater;      ncond = Assembler::lessEqual;    break;
     case lir_cond_belowEqual:   acond = Assembler::belowEqual;   ncond = Assembler::above;        break;
     case lir_cond_aboveEqual:   acond = Assembler::aboveEqual;   ncond = Assembler::below;        break;
-    default:                    ShouldNotReachHere();
+    default:                    acond = Assembler::equal;        ncond = Assembler::notEqual;
+                                ShouldNotReachHere();
   }
 
   if (opr1->is_cpu_register()) {
@@ -3237,27 +3238,23 @@
   assert(default_type != NULL && default_type->is_array_klass() && default_type->is_loaded(), "must be true at this point");
 
   int elem_size = type2aelembytes(basic_type);
-  int shift_amount;
   Address::ScaleFactor scale;
 
   switch (elem_size) {
     case 1 :
-      shift_amount = 0;
       scale = Address::times_1;
       break;
     case 2 :
-      shift_amount = 1;
       scale = Address::times_2;
       break;
     case 4 :
-      shift_amount = 2;
       scale = Address::times_4;
       break;
     case 8 :
-      shift_amount = 3;
       scale = Address::times_8;
       break;
     default:
+      scale = Address::no_scale;
       ShouldNotReachHere();
   }
 
@@ -3278,6 +3275,23 @@
     __ jcc(Assembler::zero, *stub->entry());
   }
 
+  // If the compiler was not able to prove that exact type of the source or the destination
+  // of the arraycopy is an array type, check at runtime if the source or the destination is
+  // an instance type.
+  if (flags & LIR_OpArrayCopy::type_check) {
+    if (!(flags & LIR_OpArrayCopy::dst_objarray)) {
+      __ load_klass(tmp, dst);
+      __ cmpl(Address(tmp, in_bytes(Klass::layout_helper_offset())), Klass::_lh_neutral_value);
+      __ jcc(Assembler::greaterEqual, *stub->entry());
+    }
+
+    if (!(flags & LIR_OpArrayCopy::src_objarray)) {
+      __ load_klass(tmp, src);
+      __ cmpl(Address(tmp, in_bytes(Klass::layout_helper_offset())), Klass::_lh_neutral_value);
+      __ jcc(Assembler::greaterEqual, *stub->entry());
+    }
+  }
+
   // check if negative
   if (flags & LIR_OpArrayCopy::src_pos_positive_check) {
     __ testl(src_pos, src_pos);
--- a/src/cpu/x86/vm/c1_LIRGenerator_x86.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/cpu/x86/vm/c1_LIRGenerator_x86.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -195,7 +195,7 @@
 
 
 LIR_Opr LIRGenerator::load_immediate(int x, BasicType type) {
-  LIR_Opr r;
+  LIR_Opr r = NULL;
   if (type == T_LONG) {
     r = LIR_OprFact::longConst(x);
   } else if (type == T_INT) {
@@ -485,7 +485,7 @@
     __ cmp(lir_cond_equal, right.result(), LIR_OprFact::longConst(0));
     __ branch(lir_cond_equal, T_LONG, new DivByZeroStub(info));
 
-    address entry;
+    address entry = NULL;
     switch (x->op()) {
     case Bytecodes::_lrem:
       entry = CAST_FROM_FN_PTR(address, SharedRuntime::lrem);
@@ -1025,7 +1025,7 @@
 
 void LIRGenerator::do_Convert(Convert* x) {
   // flags that vary for the different operations and different SSE-settings
-  bool fixed_input, fixed_result, round_result, needs_stub;
+  bool fixed_input = false, fixed_result = false, round_result = false, needs_stub = false;
 
   switch (x->op()) {
     case Bytecodes::_i2l: // fall through
--- a/src/cpu/x86/vm/jniFastGetField_x86_32.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/cpu/x86/vm/jniFastGetField_x86_32.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -48,7 +48,7 @@
 // between loads, which is much more efficient than lfence.
 
 address JNI_FastGetField::generate_fast_get_int_field0(BasicType type) {
-  const char *name;
+  const char *name = NULL;
   switch (type) {
     case T_BOOLEAN: name = "jni_fast_GetBooleanField"; break;
     case T_BYTE:    name = "jni_fast_GetByteField";    break;
@@ -122,7 +122,7 @@
 
   slowcase_entry_pclist[count++] = __ pc();
   __ bind (slow);
-  address slow_case_addr;
+  address slow_case_addr = NULL;
   switch (type) {
     case T_BOOLEAN: slow_case_addr = jni_GetBooleanField_addr(); break;
     case T_BYTE:    slow_case_addr = jni_GetByteField_addr();    break;
@@ -256,7 +256,7 @@
 }
 
 address JNI_FastGetField::generate_fast_get_float_field0(BasicType type) {
-  const char *name;
+  const char *name = NULL;
   switch (type) {
     case T_FLOAT:  name = "jni_fast_GetFloatField";  break;
     case T_DOUBLE: name = "jni_fast_GetDoubleField"; break;
@@ -337,7 +337,7 @@
 
   slowcase_entry_pclist[count++] = __ pc();
   __ bind (slow);
-  address slow_case_addr;
+  address slow_case_addr = NULL;
   switch (type) {
     case T_FLOAT:  slow_case_addr = jni_GetFloatField_addr();  break;
     case T_DOUBLE: slow_case_addr = jni_GetDoubleField_addr(); break;
--- a/src/cpu/x86/vm/jniFastGetField_x86_64.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/cpu/x86/vm/jniFastGetField_x86_64.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -51,7 +51,7 @@
 // since that may scratch r10!
 
 address JNI_FastGetField::generate_fast_get_int_field0(BasicType type) {
-  const char *name;
+  const char *name = NULL;
   switch (type) {
     case T_BOOLEAN: name = "jni_fast_GetBooleanField"; break;
     case T_BYTE:    name = "jni_fast_GetByteField";    break;
@@ -111,7 +111,7 @@
 
   slowcase_entry_pclist[count++] = __ pc();
   __ bind (slow);
-  address slow_case_addr;
+  address slow_case_addr = NULL;
   switch (type) {
     case T_BOOLEAN: slow_case_addr = jni_GetBooleanField_addr(); break;
     case T_BYTE:    slow_case_addr = jni_GetByteField_addr();    break;
@@ -153,7 +153,7 @@
 }
 
 address JNI_FastGetField::generate_fast_get_float_field0(BasicType type) {
-  const char *name;
+  const char *name = NULL;
   switch (type) {
     case T_FLOAT:     name = "jni_fast_GetFloatField";     break;
     case T_DOUBLE:    name = "jni_fast_GetDoubleField";    break;
@@ -206,7 +206,7 @@
 
   slowcase_entry_pclist[count++] = __ pc();
   __ bind (slow);
-  address slow_case_addr;
+  address slow_case_addr = NULL;
   switch (type) {
     case T_FLOAT:     slow_case_addr = jni_GetFloatField_addr();  break;
     case T_DOUBLE:    slow_case_addr = jni_GetDoubleField_addr();
--- a/src/cpu/x86/vm/macroAssembler_x86.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/cpu/x86/vm/macroAssembler_x86.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -3202,7 +3202,24 @@
     jmp(done);
   } else {
     // Stack: X Y
-    Label x_negative, y_odd;
+    Label x_negative, y_not_2;
+
+    static double two = 2.0;
+    ExternalAddress two_addr((address)&two);
+
+    // constant maybe too far on 64 bit
+    lea(tmp2, two_addr);
+    fld_d(Address(tmp2, 0));    // Stack: 2 X Y
+    fcmp(tmp, 2, true, false);  // Stack: X Y
+    jcc(Assembler::parity, y_not_2);
+    jcc(Assembler::notEqual, y_not_2);
+
+    fxch(); fpop();             // Stack: X
+    fmul(0);                    // Stack: X*X
+
+    jmp(done);
+
+    bind(y_not_2);
 
     fldz();                     // Stack: 0 X Y
     fcmp(tmp, 1, true, false);  // Stack: X Y
@@ -7769,6 +7786,503 @@
   pop(tmp2);
   pop(tmp1);
 }
+
+//Helper functions for square_to_len()
+
+/**
+ * Store the squares of x[], right shifted one bit (divided by 2) into z[]
+ * Preserves x and z and modifies rest of the registers.
+ */
+
+void MacroAssembler::square_rshift(Register x, Register xlen, Register z, Register tmp1, Register tmp3, Register tmp4, Register tmp5, Register rdxReg, Register raxReg) {
+  // Perform square and right shift by 1
+  // Handle odd xlen case first, then for even xlen do the following
+  // jlong carry = 0;
+  // for (int j=0, i=0; j < xlen; j+=2, i+=4) {
+  //     huge_128 product = x[j:j+1] * x[j:j+1];
+  //     z[i:i+1] = (carry << 63) | (jlong)(product >>> 65);
+  //     z[i+2:i+3] = (jlong)(product >>> 1);
+  //     carry = (jlong)product;
+  // }
+
+  xorq(tmp5, tmp5);     // carry
+  xorq(rdxReg, rdxReg);
+  xorl(tmp1, tmp1);     // index for x
+  xorl(tmp4, tmp4);     // index for z
+
+  Label L_first_loop, L_first_loop_exit;
+
+  testl(xlen, 1);
+  jccb(Assembler::zero, L_first_loop); //jump if xlen is even
+
+  // Square and right shift by 1 the odd element using 32 bit multiply
+  movl(raxReg, Address(x, tmp1, Address::times_4, 0));
+  imulq(raxReg, raxReg);
+  shrq(raxReg, 1);
+  adcq(tmp5, 0);
+  movq(Address(z, tmp4, Address::times_4, 0), raxReg);
+  incrementl(tmp1);
+  addl(tmp4, 2);
+
+  // Square and  right shift by 1 the rest using 64 bit multiply
+  bind(L_first_loop);
+  cmpptr(tmp1, xlen);
+  jccb(Assembler::equal, L_first_loop_exit);
+
+  // Square
+  movq(raxReg, Address(x, tmp1, Address::times_4,  0));
+  rorq(raxReg, 32);    // convert big-endian to little-endian
+  mulq(raxReg);        // 64-bit multiply rax * rax -> rdx:rax
+
+  // Right shift by 1 and save carry
+  shrq(tmp5, 1);       // rdx:rax:tmp5 = (tmp5:rdx:rax) >>> 1
+  rcrq(rdxReg, 1);
+  rcrq(raxReg, 1);
+  adcq(tmp5, 0);
+
+  // Store result in z
+  movq(Address(z, tmp4, Address::times_4, 0), rdxReg);
+  movq(Address(z, tmp4, Address::times_4, 8), raxReg);
+
+  // Update indices for x and z
+  addl(tmp1, 2);
+  addl(tmp4, 4);
+  jmp(L_first_loop);
+
+  bind(L_first_loop_exit);
+}
+
+
+/**
+ * Perform the following multiply add operation using BMI2 instructions
+ * carry:sum = sum + op1*op2 + carry
+ * op2 should be in rdx
+ * op2 is preserved, all other registers are modified
+ */
+void MacroAssembler::multiply_add_64_bmi2(Register sum, Register op1, Register op2, Register carry, Register tmp2) {
+  // assert op2 is rdx
+  mulxq(tmp2, op1, op1);  //  op1 * op2 -> tmp2:op1
+  addq(sum, carry);
+  adcq(tmp2, 0);
+  addq(sum, op1);
+  adcq(tmp2, 0);
+  movq(carry, tmp2);
+}
+
+/**
+ * Perform the following multiply add operation:
+ * carry:sum = sum + op1*op2 + carry
+ * Preserves op1, op2 and modifies rest of registers
+ */
+void MacroAssembler::multiply_add_64(Register sum, Register op1, Register op2, Register carry, Register rdxReg, Register raxReg) {
+  // rdx:rax = op1 * op2
+  movq(raxReg, op2);
+  mulq(op1);
+
+  //  rdx:rax = sum + carry + rdx:rax
+  addq(sum, carry);
+  adcq(rdxReg, 0);
+  addq(sum, raxReg);
+  adcq(rdxReg, 0);
+
+  // carry:sum = rdx:sum
+  movq(carry, rdxReg);
+}
+
+/**
+ * Add 64 bit long carry into z[] with carry propogation.
+ * Preserves z and carry register values and modifies rest of registers.
+ *
+ */
+void MacroAssembler::add_one_64(Register z, Register zlen, Register carry, Register tmp1) {
+  Label L_fourth_loop, L_fourth_loop_exit;
+
+  movl(tmp1, 1);
+  subl(zlen, 2);
+  addq(Address(z, zlen, Address::times_4, 0), carry);
+
+  bind(L_fourth_loop);
+  jccb(Assembler::carryClear, L_fourth_loop_exit);
+  subl(zlen, 2);
+  jccb(Assembler::negative, L_fourth_loop_exit);
+  addq(Address(z, zlen, Address::times_4, 0), tmp1);
+  jmp(L_fourth_loop);
+  bind(L_fourth_loop_exit);
+}
+
+/**
+ * Shift z[] left by 1 bit.
+ * Preserves x, len, z and zlen registers and modifies rest of the registers.
+ *
+ */
+void MacroAssembler::lshift_by_1(Register x, Register len, Register z, Register zlen, Register tmp1, Register tmp2, Register tmp3, Register tmp4) {
+
+  Label L_fifth_loop, L_fifth_loop_exit;
+
+  // Fifth loop
+  // Perform primitiveLeftShift(z, zlen, 1)
+
+  const Register prev_carry = tmp1;
+  const Register new_carry = tmp4;
+  const Register value = tmp2;
+  const Register zidx = tmp3;
+
+  // int zidx, carry;
+  // long value;
+  // carry = 0;
+  // for (zidx = zlen-2; zidx >=0; zidx -= 2) {
+  //    (carry:value)  = (z[i] << 1) | carry ;
+  //    z[i] = value;
+  // }
+
+  movl(zidx, zlen);
+  xorl(prev_carry, prev_carry); // clear carry flag and prev_carry register
+
+  bind(L_fifth_loop);
+  decl(zidx);  // Use decl to preserve carry flag
+  decl(zidx);
+  jccb(Assembler::negative, L_fifth_loop_exit);
+
+  if (UseBMI2Instructions) {
+     movq(value, Address(z, zidx, Address::times_4, 0));
+     rclq(value, 1);
+     rorxq(value, value, 32);
+     movq(Address(z, zidx, Address::times_4,  0), value);  // Store back in big endian form
+  }
+  else {
+    // clear new_carry
+    xorl(new_carry, new_carry);
+
+    // Shift z[i] by 1, or in previous carry and save new carry
+    movq(value, Address(z, zidx, Address::times_4, 0));
+    shlq(value, 1);
+    adcl(new_carry, 0);
+
+    orq(value, prev_carry);
+    rorq(value, 0x20);
+    movq(Address(z, zidx, Address::times_4,  0), value);  // Store back in big endian form
+
+    // Set previous carry = new carry
+    movl(prev_carry, new_carry);
+  }
+  jmp(L_fifth_loop);
+
+  bind(L_fifth_loop_exit);
+}
+
+
+/**
+ * Code for BigInteger::squareToLen() intrinsic
+ *
+ * rdi: x
+ * rsi: len
+ * r8:  z
+ * rcx: zlen
+ * r12: tmp1
+ * r13: tmp2
+ * r14: tmp3
+ * r15: tmp4
+ * rbx: tmp5
+ *
+ */
+void MacroAssembler::square_to_len(Register x, Register len, Register z, Register zlen, Register tmp1, Register tmp2, Register tmp3, Register tmp4, Register tmp5, Register rdxReg, Register raxReg) {
+
+  Label L_second_loop, L_second_loop_exit, L_third_loop, L_third_loop_exit, fifth_loop, fifth_loop_exit, L_last_x, L_multiply;
+  push(tmp1);
+  push(tmp2);
+  push(tmp3);
+  push(tmp4);
+  push(tmp5);
+
+  // First loop
+  // Store the squares, right shifted one bit (i.e., divided by 2).
+  square_rshift(x, len, z, tmp1, tmp3, tmp4, tmp5, rdxReg, raxReg);
+
+  // Add in off-diagonal sums.
+  //
+  // Second, third (nested) and fourth loops.
+  // zlen +=2;
+  // for (int xidx=len-2,zidx=zlen-4; xidx > 0; xidx-=2,zidx-=4) {
+  //    carry = 0;
+  //    long op2 = x[xidx:xidx+1];
+  //    for (int j=xidx-2,k=zidx; j >= 0; j-=2) {
+  //       k -= 2;
+  //       long op1 = x[j:j+1];
+  //       long sum = z[k:k+1];
+  //       carry:sum = multiply_add_64(sum, op1, op2, carry, tmp_regs);
+  //       z[k:k+1] = sum;
+  //    }
+  //    add_one_64(z, k, carry, tmp_regs);
+  // }
+
+  const Register carry = tmp5;
+  const Register sum = tmp3;
+  const Register op1 = tmp4;
+  Register op2 = tmp2;
+
+  push(zlen);
+  push(len);
+  addl(zlen,2);
+  bind(L_second_loop);
+  xorq(carry, carry);
+  subl(zlen, 4);
+  subl(len, 2);
+  push(zlen);
+  push(len);
+  cmpl(len, 0);
+  jccb(Assembler::lessEqual, L_second_loop_exit);
+
+  // Multiply an array by one 64 bit long.
+  if (UseBMI2Instructions) {
+    op2 = rdxReg;
+    movq(op2, Address(x, len, Address::times_4,  0));
+    rorxq(op2, op2, 32);
+  }
+  else {
+    movq(op2, Address(x, len, Address::times_4,  0));
+    rorq(op2, 32);
+  }
+
+  bind(L_third_loop);
+  decrementl(len);
+  jccb(Assembler::negative, L_third_loop_exit);
+  decrementl(len);
+  jccb(Assembler::negative, L_last_x);
+
+  movq(op1, Address(x, len, Address::times_4,  0));
+  rorq(op1, 32);
+
+  bind(L_multiply);
+  subl(zlen, 2);
+  movq(sum, Address(z, zlen, Address::times_4,  0));
+
+  // Multiply 64 bit by 64 bit and add 64 bits lower half and upper 64 bits as carry.
+  if (UseBMI2Instructions) {
+    multiply_add_64_bmi2(sum, op1, op2, carry, tmp2);
+  }
+  else {
+    multiply_add_64(sum, op1, op2, carry, rdxReg, raxReg);
+  }
+
+  movq(Address(z, zlen, Address::times_4, 0), sum);
+
+  jmp(L_third_loop);
+  bind(L_third_loop_exit);
+
+  // Fourth loop
+  // Add 64 bit long carry into z with carry propogation.
+  // Uses offsetted zlen.
+  add_one_64(z, zlen, carry, tmp1);
+
+  pop(len);
+  pop(zlen);
+  jmp(L_second_loop);
+
+  // Next infrequent code is moved outside loops.
+  bind(L_last_x);
+  movl(op1, Address(x, 0));
+  jmp(L_multiply);
+
+  bind(L_second_loop_exit);
+  pop(len);
+  pop(zlen);
+  pop(len);
+  pop(zlen);
+
+  // Fifth loop
+  // Shift z left 1 bit.
+  lshift_by_1(x, len, z, zlen, tmp1, tmp2, tmp3, tmp4);
+
+  // z[zlen-1] |= x[len-1] & 1;
+  movl(tmp3, Address(x, len, Address::times_4, -4));
+  andl(tmp3, 1);
+  orl(Address(z, zlen, Address::times_4,  -4), tmp3);
+
+  pop(tmp5);
+  pop(tmp4);
+  pop(tmp3);
+  pop(tmp2);
+  pop(tmp1);
+}
+
+/**
+ * Helper function for mul_add()
+ * Multiply the in[] by int k and add to out[] starting at offset offs using
+ * 128 bit by 32 bit multiply and return the carry in tmp5.
+ * Only quad int aligned length of in[] is operated on in this function.
+ * k is in rdxReg for BMI2Instructions, for others it is in tmp2.
+ * This function preserves out, in and k registers.
+ * len and offset point to the appropriate index in "in" & "out" correspondingly
+ * tmp5 has the carry.
+ * other registers are temporary and are modified.
+ *
+ */
+void MacroAssembler::mul_add_128_x_32_loop(Register out, Register in,
+  Register offset, Register len, Register tmp1, Register tmp2, Register tmp3,
+  Register tmp4, Register tmp5, Register rdxReg, Register raxReg) {
+
+  Label L_first_loop, L_first_loop_exit;
+
+  movl(tmp1, len);
+  shrl(tmp1, 2);
+
+  bind(L_first_loop);
+  subl(tmp1, 1);
+  jccb(Assembler::negative, L_first_loop_exit);
+
+  subl(len, 4);
+  subl(offset, 4);
+
+  Register op2 = tmp2;
+  const Register sum = tmp3;
+  const Register op1 = tmp4;
+  const Register carry = tmp5;
+
+  if (UseBMI2Instructions) {
+    op2 = rdxReg;
+  }
+
+  movq(op1, Address(in, len, Address::times_4,  8));
+  rorq(op1, 32);
+  movq(sum, Address(out, offset, Address::times_4,  8));
+  rorq(sum, 32);
+  if (UseBMI2Instructions) {
+    multiply_add_64_bmi2(sum, op1, op2, carry, raxReg);
+  }
+  else {
+    multiply_add_64(sum, op1, op2, carry, rdxReg, raxReg);
+  }
+  // Store back in big endian from little endian
+  rorq(sum, 0x20);
+  movq(Address(out, offset, Address::times_4,  8), sum);
+
+  movq(op1, Address(in, len, Address::times_4,  0));
+  rorq(op1, 32);
+  movq(sum, Address(out, offset, Address::times_4,  0));
+  rorq(sum, 32);
+  if (UseBMI2Instructions) {
+    multiply_add_64_bmi2(sum, op1, op2, carry, raxReg);
+  }
+  else {
+    multiply_add_64(sum, op1, op2, carry, rdxReg, raxReg);
+  }
+  // Store back in big endian from little endian
+  rorq(sum, 0x20);
+  movq(Address(out, offset, Address::times_4,  0), sum);
+
+  jmp(L_first_loop);
+  bind(L_first_loop_exit);
+}
+
+/**
+ * Code for BigInteger::mulAdd() intrinsic
+ *
+ * rdi: out
+ * rsi: in
+ * r11: offs (out.length - offset)
+ * rcx: len
+ * r8:  k
+ * r12: tmp1
+ * r13: tmp2
+ * r14: tmp3
+ * r15: tmp4
+ * rbx: tmp5
+ * Multiply the in[] by word k and add to out[], return the carry in rax
+ */
+void MacroAssembler::mul_add(Register out, Register in, Register offs,
+   Register len, Register k, Register tmp1, Register tmp2, Register tmp3,
+   Register tmp4, Register tmp5, Register rdxReg, Register raxReg) {
+
+  Label L_carry, L_last_in, L_done;
+
+// carry = 0;
+// for (int j=len-1; j >= 0; j--) {
+//    long product = (in[j] & LONG_MASK) * kLong +
+//                   (out[offs] & LONG_MASK) + carry;
+//    out[offs--] = (int)product;
+//    carry = product >>> 32;
+// }
+//
+  push(tmp1);
+  push(tmp2);
+  push(tmp3);
+  push(tmp4);
+  push(tmp5);
+
+  Register op2 = tmp2;
+  const Register sum = tmp3;
+  const Register op1 = tmp4;
+  const Register carry =  tmp5;
+
+  if (UseBMI2Instructions) {
+    op2 = rdxReg;
+    movl(op2, k);
+  }
+  else {
+    movl(op2, k);
+  }
+
+  xorq(carry, carry);
+
+  //First loop
+
+  //Multiply in[] by k in a 4 way unrolled loop using 128 bit by 32 bit multiply
+  //The carry is in tmp5
+  mul_add_128_x_32_loop(out, in, offs, len, tmp1, tmp2, tmp3, tmp4, tmp5, rdxReg, raxReg);
+
+  //Multiply the trailing in[] entry using 64 bit by 32 bit, if any
+  decrementl(len);
+  jccb(Assembler::negative, L_carry);
+  decrementl(len);
+  jccb(Assembler::negative, L_last_in);
+
+  movq(op1, Address(in, len, Address::times_4,  0));
+  rorq(op1, 32);
+
+  subl(offs, 2);
+  movq(sum, Address(out, offs, Address::times_4,  0));
+  rorq(sum, 32);
+
+  if (UseBMI2Instructions) {
+    multiply_add_64_bmi2(sum, op1, op2, carry, raxReg);
+  }
+  else {
+    multiply_add_64(sum, op1, op2, carry, rdxReg, raxReg);
+  }
+
+  // Store back in big endian from little endian
+  rorq(sum, 0x20);
+  movq(Address(out, offs, Address::times_4,  0), sum);
+
+  testl(len, len);
+  jccb(Assembler::zero, L_carry);
+
+  //Multiply the last in[] entry, if any
+  bind(L_last_in);
+  movl(op1, Address(in, 0));
+  movl(sum, Address(out, offs, Address::times_4,  -4));
+
+  movl(raxReg, k);
+  mull(op1); //tmp4 * eax -> edx:eax
+  addl(sum, carry);
+  adcl(rdxReg, 0);
+  addl(sum, raxReg);
+  adcl(rdxReg, 0);
+  movl(carry, rdxReg);
+
+  movl(Address(out, offs, Address::times_4,  -4), sum);
+
+  bind(L_carry);
+  //return tmp5/carry as carry in rax
+  movl(rax, carry);
+
+  bind(L_done);
+  pop(tmp5);
+  pop(tmp4);
+  pop(tmp3);
+  pop(tmp2);
+  pop(tmp1);
+}
 #endif
 
 /**
--- a/src/cpu/x86/vm/macroAssembler_x86.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/cpu/x86/vm/macroAssembler_x86.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1241,6 +1241,25 @@
                                Register carry2);
   void multiply_to_len(Register x, Register xlen, Register y, Register ylen, Register z, Register zlen,
                        Register tmp1, Register tmp2, Register tmp3, Register tmp4, Register tmp5);
+
+  void square_rshift(Register x, Register len, Register z, Register tmp1, Register tmp3,
+                     Register tmp4, Register tmp5, Register rdxReg, Register raxReg);
+  void multiply_add_64_bmi2(Register sum, Register op1, Register op2, Register carry,
+                            Register tmp2);
+  void multiply_add_64(Register sum, Register op1, Register op2, Register carry,
+                       Register rdxReg, Register raxReg);
+  void add_one_64(Register z, Register zlen, Register carry, Register tmp1);
+  void lshift_by_1(Register x, Register len, Register z, Register zlen, Register tmp1, Register tmp2,
+                       Register tmp3, Register tmp4);
+  void square_to_len(Register x, Register len, Register z, Register zlen, Register tmp1, Register tmp2,
+                     Register tmp3, Register tmp4, Register tmp5, Register rdxReg, Register raxReg);
+
+  void mul_add_128_x_32_loop(Register out, Register in, Register offset, Register len, Register tmp1,
+               Register tmp2, Register tmp3, Register tmp4, Register tmp5, Register rdxReg,
+               Register raxReg);
+  void mul_add(Register out, Register in, Register offset, Register len, Register k, Register tmp1,
+               Register tmp2, Register tmp3, Register tmp4, Register tmp5, Register rdxReg,
+               Register raxReg);
 #endif
 
   // CRC32 code for java.util.zip.CRC32::updateBytes() instrinsic.
--- a/src/cpu/x86/vm/sharedRuntime_x86_64.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/cpu/x86/vm/sharedRuntime_x86_64.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -23,6 +23,9 @@
  */
 
 #include "precompiled.hpp"
+#ifndef _WINDOWS
+#include "alloca.h"
+#endif
 #include "asm/macroAssembler.hpp"
 #include "asm/macroAssembler.inline.hpp"
 #include "code/debugInfoRec.hpp"
@@ -4079,6 +4082,256 @@
 }
 
 
+//------------------------------Montgomery multiplication------------------------
+//
+
+#ifndef _WINDOWS
+
+#define ASM_SUBTRACT
+
+#ifdef ASM_SUBTRACT
+// Subtract 0:b from carry:a.  Return carry.
+static unsigned long
+sub(unsigned long a[], unsigned long b[], unsigned long carry, long len) {
+  long i = 0, cnt = len;
+  unsigned long tmp;
+  asm volatile("clc; "
+               "0: ; "
+               "mov (%[b], %[i], 8), %[tmp]; "
+               "sbb %[tmp], (%[a], %[i], 8); "
+               "inc %[i]; dec %[cnt]; "
+               "jne 0b; "
+               "mov %[carry], %[tmp]; sbb $0, %[tmp]; "
+               : [i]"+r"(i), [cnt]"+r"(cnt), [tmp]"=&r"(tmp)
+               : [a]"r"(a), [b]"r"(b), [carry]"r"(carry)
+               : "memory");
+  return tmp;
+}
+#else // ASM_SUBTRACT
+typedef int __attribute__((mode(TI))) int128;
+
+// Subtract 0:b from carry:a.  Return carry.
+static unsigned long
+sub(unsigned long a[], unsigned long b[], unsigned long carry, int len) {
+  int128 tmp = 0;
+  int i;
+  for (i = 0; i < len; i++) {
+    tmp += a[i];
+    tmp -= b[i];
+    a[i] = tmp;
+    tmp >>= 64;
+    assert(-1 <= tmp && tmp <= 0, "invariant");
+  }
+  return tmp + carry;
+}
+#endif // ! ASM_SUBTRACT
+
+// Multiply (unsigned) Long A by Long B, accumulating the double-
+// length result into the accumulator formed of T0, T1, and T2.
+#define MACC(A, B, T0, T1, T2)                                      \
+do {                                                                \
+  unsigned long hi, lo;                                             \
+  asm volatile("mul %5; add %%rax, %2; adc %%rdx, %3; adc $0, %4"   \
+           : "=&d"(hi), "=a"(lo), "+r"(T0), "+r"(T1), "+g"(T2)      \
+           : "r"(A), "a"(B) : "cc");                                \
+ } while(0)
+
+// As above, but add twice the double-length result into the
+// accumulator.
+#define MACC2(A, B, T0, T1, T2)                                     \
+do {                                                                \
+  unsigned long hi, lo;                                             \
+  asm volatile("mul %5; add %%rax, %2; adc %%rdx, %3; adc $0, %4;"  \
+           "add %%rax, %2; adc %%rdx, %3; adc $0, %4"               \
+           : "=&d"(hi), "=a"(lo), "+r"(T0), "+r"(T1), "+g"(T2)      \
+           : "r"(A), "a"(B) : "cc");                                \
+ } while(0)
+
+// Fast Montgomery multiplication.  The derivation of the algorithm is
+// in  A Cryptographic Library for the Motorola DSP56000,
+// Dusse and Kaliski, Proc. EUROCRYPT 90, pp. 230-237.
+
+static void __attribute__((noinline))
+montgomery_multiply(unsigned long a[], unsigned long b[], unsigned long n[],
+                    unsigned long m[], unsigned long inv, int len) {
+  unsigned long t0 = 0, t1 = 0, t2 = 0; // Triple-precision accumulator
+  int i;
+
+  assert(inv * n[0] == -1UL, "broken inverse in Montgomery multiply");
+
+  for (i = 0; i < len; i++) {
+    int j;
+    for (j = 0; j < i; j++) {
+      MACC(a[j], b[i-j], t0, t1, t2);
+      MACC(m[j], n[i-j], t0, t1, t2);
+    }
+    MACC(a[i], b[0], t0, t1, t2);
+    m[i] = t0 * inv;
+    MACC(m[i], n[0], t0, t1, t2);
+
+    assert(t0 == 0, "broken Montgomery multiply");
+
+    t0 = t1; t1 = t2; t2 = 0;
+  }
+
+  for (i = len; i < 2*len; i++) {
+    int j;
+    for (j = i-len+1; j < len; j++) {
+      MACC(a[j], b[i-j], t0, t1, t2);
+      MACC(m[j], n[i-j], t0, t1, t2);
+    }
+    m[i-len] = t0;
+    t0 = t1; t1 = t2; t2 = 0;
+  }
+
+  while (t0)
+    t0 = sub(m, n, t0, len);
+}
+
+// Fast Montgomery squaring.  This uses asymptotically 25% fewer
+// multiplies so it should be up to 25% faster than Montgomery
+// multiplication.  However, its loop control is more complex and it
+// may actually run slower on some machines.
+
+static void __attribute__((noinline))
+montgomery_square(unsigned long a[], unsigned long n[],
+                  unsigned long m[], unsigned long inv, int len) {
+  unsigned long t0 = 0, t1 = 0, t2 = 0; // Triple-precision accumulator
+  int i;
+
+  assert(inv * n[0] == -1UL, "broken inverse in Montgomery multiply");
+
+  for (i = 0; i < len; i++) {
+    int j;
+    int end = (i+1)/2;
+    for (j = 0; j < end; j++) {
+      MACC2(a[j], a[i-j], t0, t1, t2);
+      MACC(m[j], n[i-j], t0, t1, t2);
+    }
+    if ((i & 1) == 0) {
+      MACC(a[j], a[j], t0, t1, t2);
+    }
+    for (; j < i; j++) {
+      MACC(m[j], n[i-j], t0, t1, t2);
+    }
+    m[i] = t0 * inv;
+    MACC(m[i], n[0], t0, t1, t2);
+
+    assert(t0 == 0, "broken Montgomery square");
+
+    t0 = t1; t1 = t2; t2 = 0;
+  }
+
+  for (i = len; i < 2*len; i++) {
+    int start = i-len+1;
+    int end = start + (len - start)/2;
+    int j;
+    for (j = start; j < end; j++) {
+      MACC2(a[j], a[i-j], t0, t1, t2);
+      MACC(m[j], n[i-j], t0, t1, t2);
+    }
+    if ((i & 1) == 0) {
+      MACC(a[j], a[j], t0, t1, t2);
+    }
+    for (; j < len; j++) {
+      MACC(m[j], n[i-j], t0, t1, t2);
+    }
+    m[i-len] = t0;
+    t0 = t1; t1 = t2; t2 = 0;
+  }
+
+  while (t0)
+    t0 = sub(m, n, t0, len);
+}
+
+// Swap words in a longword.
+static unsigned long swap(unsigned long x) {
+  return (x << 32) | (x >> 32);
+}
+
+// Copy len longwords from s to d, word-swapping as we go.  The
+// destination array is reversed.
+static void reverse_words(unsigned long *s, unsigned long *d, int len) {
+  d += len;
+  while(len-- > 0) {
+    d--;
+    *d = swap(*s);
+    s++;
+  }
+}
+
+// The threshold at which squaring is advantageous was determined
+// experimentally on an i7-3930K (Ivy Bridge) CPU @ 3.5GHz.
+#define MONTGOMERY_SQUARING_THRESHOLD 64
+
+void SharedRuntime::montgomery_multiply(jint *a_ints, jint *b_ints, jint *n_ints,
+                                        jint len, jlong inv,
+                                        jint *m_ints) {
+  assert(len % 2 == 0, "array length in montgomery_multiply must be even");
+  int longwords = len/2;
+
+  // Make very sure we don't use so much space that the stack might
+  // overflow.  512 jints corresponds to an 16384-bit integer and
+  // will use here a total of 8k bytes of stack space.
+  int total_allocation = longwords * sizeof (unsigned long) * 4;
+  guarantee(total_allocation <= 8192, "must be");
+  unsigned long *scratch = (unsigned long *)alloca(total_allocation);
+
+  // Local scratch arrays
+  unsigned long
+    *a = scratch + 0 * longwords,
+    *b = scratch + 1 * longwords,
+    *n = scratch + 2 * longwords,
+    *m = scratch + 3 * longwords;
+
+  reverse_words((unsigned long *)a_ints, a, longwords);
+  reverse_words((unsigned long *)b_ints, b, longwords);
+  reverse_words((unsigned long *)n_ints, n, longwords);
+
+  ::montgomery_multiply(a, b, n, m, (unsigned long)inv, longwords);
+
+  reverse_words(m, (unsigned long *)m_ints, longwords);
+}
+
+void SharedRuntime::montgomery_square(jint *a_ints, jint *n_ints,
+                                      jint len, jlong inv,
+                                      jint *m_ints) {
+  assert(len % 2 == 0, "array length in montgomery_square must be even");
+  int longwords = len/2;
+
+  // Make very sure we don't use so much space that the stack might
+  // overflow.  512 jints corresponds to an 16384-bit integer and
+  // will use here a total of 6k bytes of stack space.
+  int total_allocation = longwords * sizeof (unsigned long) * 3;
+  guarantee(total_allocation <= 8192, "must be");
+  unsigned long *scratch = (unsigned long *)alloca(total_allocation);
+
+  // Local scratch arrays
+  unsigned long
+    *a = scratch + 0 * longwords,
+    *n = scratch + 1 * longwords,
+    *m = scratch + 2 * longwords;
+
+  reverse_words((unsigned long *)a_ints, a, longwords);
+  reverse_words((unsigned long *)n_ints, n, longwords);
+
+  //montgomery_square fails to pass BigIntegerTest on solaris amd64
+  //on jdk7 and jdk8.
+#ifndef SOLARIS
+  if (len >= MONTGOMERY_SQUARING_THRESHOLD) {
+#else
+  if (0) {
+#endif
+    ::montgomery_square(a, n, m, (unsigned long)inv, longwords);
+  } else {
+    ::montgomery_multiply(a, a, n, m, (unsigned long)inv, longwords);
+  }
+
+  reverse_words(m, (unsigned long *)m_ints, longwords);
+}
+
+#endif // WINDOWS
+
 #ifdef COMPILER2
 // This is here instead of runtime_x86_64.cpp because it uses SimpleRuntimeFrame
 //
--- a/src/cpu/x86/vm/stubGenerator_x86_64.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/cpu/x86/vm/stubGenerator_x86_64.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -3743,6 +3743,107 @@
     return start;
   }
 
+/**
+   *  Arguments:
+   *
+  //  Input:
+  //    c_rarg0   - x address
+  //    c_rarg1   - x length
+  //    c_rarg2   - z address
+  //    c_rarg3   - z lenth
+   *
+   */
+  address generate_squareToLen() {
+
+    __ align(CodeEntryAlignment);
+    StubCodeMark mark(this, "StubRoutines", "squareToLen");
+
+    address start = __ pc();
+    // Win64: rcx, rdx, r8, r9 (c_rarg0, c_rarg1, ...)
+    // Unix:  rdi, rsi, rdx, rcx (c_rarg0, c_rarg1, ...)
+    const Register x      = rdi;
+    const Register len    = rsi;
+    const Register z      = r8;
+    const Register zlen   = rcx;
+
+   const Register tmp1      = r12;
+   const Register tmp2      = r13;
+   const Register tmp3      = r14;
+   const Register tmp4      = r15;
+   const Register tmp5      = rbx;
+
+    BLOCK_COMMENT("Entry:");
+    __ enter(); // required for proper stackwalking of RuntimeStub frame
+
+       setup_arg_regs(4); // x => rdi, len => rsi, z => rdx
+                          // zlen => rcx
+                          // r9 and r10 may be used to save non-volatile registers
+    __ movptr(r8, rdx);
+    __ square_to_len(x, len, z, zlen, tmp1, tmp2, tmp3, tmp4, tmp5, rdx, rax);
+
+    restore_arg_regs();
+
+    __ leave(); // required for proper stackwalking of RuntimeStub frame
+    __ ret(0);
+
+    return start;
+  }
+
+   /**
+   *  Arguments:
+   *
+   *  Input:
+   *    c_rarg0   - out address
+   *    c_rarg1   - in address
+   *    c_rarg2   - offset
+   *    c_rarg3   - len
+   * not Win64
+   *    c_rarg4   - k
+   * Win64
+   *    rsp+40    - k
+   */
+  address generate_mulAdd() {
+    __ align(CodeEntryAlignment);
+    StubCodeMark mark(this, "StubRoutines", "mulAdd");
+
+    address start = __ pc();
+    // Win64: rcx, rdx, r8, r9 (c_rarg0, c_rarg1, ...)
+    // Unix:  rdi, rsi, rdx, rcx, r8, r9 (c_rarg0, c_rarg1, ...)
+    const Register out     = rdi;
+    const Register in      = rsi;
+    const Register offset  = r11;
+    const Register len     = rcx;
+    const Register k       = r8;
+
+    // Next registers will be saved on stack in mul_add().
+    const Register tmp1  = r12;
+    const Register tmp2  = r13;
+    const Register tmp3  = r14;
+    const Register tmp4  = r15;
+    const Register tmp5  = rbx;
+
+    BLOCK_COMMENT("Entry:");
+    __ enter(); // required for proper stackwalking of RuntimeStub frame
+
+    setup_arg_regs(4); // out => rdi, in => rsi, offset => rdx
+                       // len => rcx, k => r8
+                       // r9 and r10 may be used to save non-volatile registers
+#ifdef _WIN64
+    // last argument is on stack on Win64
+    __ movl(k, Address(rsp, 6 * wordSize));
+#endif
+    __ movptr(r11, rdx);  // move offset in rdx to offset(r11)
+    __ mul_add(out, in, offset, len, k, tmp1, tmp2, tmp3, tmp4, tmp5, rdx, rax);
+
+    restore_arg_regs();
+
+    __ leave(); // required for proper stackwalking of RuntimeStub frame
+    __ ret(0);
+
+    return start;
+  }
+
+
 #undef __
 #define __ masm->
 
@@ -3987,7 +4088,24 @@
     if (UseMultiplyToLenIntrinsic) {
       StubRoutines::_multiplyToLen = generate_multiplyToLen();
     }
-#endif
+    if (UseSquareToLenIntrinsic) {
+      StubRoutines::_squareToLen = generate_squareToLen();
+    }
+    if (UseMulAddIntrinsic) {
+      StubRoutines::_mulAdd = generate_mulAdd();
+    }
+
+#ifndef _WINDOWS
+    if (UseMontgomeryMultiplyIntrinsic) {
+      StubRoutines::_montgomeryMultiply
+        = CAST_FROM_FN_PTR(address, SharedRuntime::montgomery_multiply);
+    }
+    if (UseMontgomerySquareIntrinsic) {
+      StubRoutines::_montgomerySquare
+        = CAST_FROM_FN_PTR(address, SharedRuntime::montgomery_square);
+    }
+#endif // WINDOWS
+#endif // COMPILER2
   }
 
  public:
--- a/src/cpu/x86/vm/stubRoutines_x86_64.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/cpu/x86/vm/stubRoutines_x86_64.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -33,7 +33,7 @@
 
 enum platform_dependent_constants {
   code_size1 = 19000,          // simply increase if too small (assembler will crash if too small)
-  code_size2 = 22000           // simply increase if too small (assembler will crash if too small)
+  code_size2 = 23000           // simply increase if too small (assembler will crash if too small)
 };
 
 class x86 {
--- a/src/cpu/x86/vm/vm_version_x86.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/cpu/x86/vm/vm_version_x86.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -707,6 +707,18 @@
   if (FLAG_IS_DEFAULT(UseMultiplyToLenIntrinsic)) {
     UseMultiplyToLenIntrinsic = true;
   }
+  if (FLAG_IS_DEFAULT(UseSquareToLenIntrinsic)) {
+    UseSquareToLenIntrinsic = false;
+  }
+  if (FLAG_IS_DEFAULT(UseMulAddIntrinsic)) {
+    UseMulAddIntrinsic = false;
+  }
+  if (FLAG_IS_DEFAULT(UseMontgomeryMultiplyIntrinsic)) {
+    UseMontgomeryMultiplyIntrinsic = false;
+  }
+  if (FLAG_IS_DEFAULT(UseMontgomerySquareIntrinsic)) {
+    UseMontgomerySquareIntrinsic = false;
+  }
 #else
   if (UseMultiplyToLenIntrinsic) {
     if (!FLAG_IS_DEFAULT(UseMultiplyToLenIntrinsic)) {
@@ -714,6 +726,30 @@
     }
     FLAG_SET_DEFAULT(UseMultiplyToLenIntrinsic, false);
   }
+  if (UseSquareToLenIntrinsic) {
+    if (!FLAG_IS_DEFAULT(UseSquareToLenIntrinsic)) {
+      warning("squareToLen intrinsic is not available in 32-bit VM");
+    }
+    FLAG_SET_DEFAULT(UseSquareToLenIntrinsic, false);
+  }
+  if (UseMulAddIntrinsic) {
+    if (!FLAG_IS_DEFAULT(UseMulAddIntrinsic)) {
+      warning("mulAdd intrinsic is not available in 32-bit VM");
+    }
+    FLAG_SET_DEFAULT(UseMulAddIntrinsic, false);
+  }
+  if (UseMontgomeryMultiplyIntrinsic) {
+    if (!FLAG_IS_DEFAULT(UseMontgomeryMultiplyIntrinsic)) {
+      warning("montgomeryMultiply intrinsic is not available in 32-bit VM");
+    }
+    FLAG_SET_DEFAULT(UseMontgomeryMultiplyIntrinsic, false);
+  }
+  if (UseMontgomerySquareIntrinsic) {
+    if (!FLAG_IS_DEFAULT(UseMontgomerySquareIntrinsic)) {
+      warning("montgomerySquare intrinsic is not available in 32-bit VM");
+    }
+    FLAG_SET_DEFAULT(UseMontgomerySquareIntrinsic, false);
+  }
 #endif
 #endif // COMPILER2
 
--- a/src/os/linux/vm/os_linux.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/os/linux/vm/os_linux.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -2755,7 +2755,7 @@
 
 
 int os::Linux::sched_getcpu_syscall(void) {
-  unsigned int cpu;
+  unsigned int cpu = 0;
   int retval = -1;
 
 #if defined(IA32)
@@ -4263,8 +4263,8 @@
       sigaddset(&(actp->sa_mask), sig);
     }
 
-    sa_handler_t hand;
-    sa_sigaction_t sa;
+    sa_handler_t hand = NULL;
+    sa_sigaction_t sa = NULL;
     bool siginfo_flag_set = (actp->sa_flags & SA_SIGINFO) != 0;
     // retrieve the chained handler
     if (siginfo_flag_set) {
@@ -4469,7 +4469,7 @@
 
 static const char* get_signal_handler_name(address handler,
                                            char* buf, int buflen) {
-  int offset;
+  int offset = 0;
   bool found = os::dll_address_to_library_name(handler, buf, buflen, &offset);
   if (found) {
     // skip directory names
--- a/src/os/posix/vm/os_posix.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/os/posix/vm/os_posix.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -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
@@ -678,6 +678,21 @@
 #if defined(IA64) && !defined(AIX)
     { SIGSEGV, SEGV_PSTKOVF, "SEGV_PSTKOVF", "Paragraph stack overflow" },
 #endif
+#if defined(__sparc) && defined(SOLARIS)
+// define Solaris Sparc M7 ADI SEGV signals
+#if !defined(SEGV_ACCADI)
+#define SEGV_ACCADI 3
+#endif
+    { SIGSEGV, SEGV_ACCADI,  "SEGV_ACCADI",  "ADI not enabled for mapped object." },
+#if !defined(SEGV_ACCDERR)
+#define SEGV_ACCDERR 4
+#endif
+    { SIGSEGV, SEGV_ACCDERR, "SEGV_ACCDERR", "ADI disrupting exception." },
+#if !defined(SEGV_ACCPERR)
+#define SEGV_ACCPERR 5
+#endif
+    { SIGSEGV, SEGV_ACCPERR, "SEGV_ACCPERR", "ADI precise exception." },
+#endif // defined(__sparc) && defined(SOLARIS)
     { SIGBUS,  BUS_ADRALN,   "BUS_ADRALN",   "Invalid address alignment." },
     { SIGBUS,  BUS_ADRERR,   "BUS_ADRERR",   "Nonexistent physical address." },
     { SIGBUS,  BUS_OBJERR,   "BUS_OBJERR",   "Object-specific hardware error." },
--- a/src/os_cpu/linux_x86/vm/copy_linux_x86.inline.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/os_cpu/linux_x86/vm/copy_linux_x86.inline.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -30,7 +30,7 @@
   (void)memmove(to, from, count * HeapWordSize);
 #else
   // Includes a zero-count check.
-  intx temp;
+  intx temp = 0;
   __asm__ volatile("        testl   %6,%6         ;"
                    "        jz      7f            ;"
                    "        cmpl    %4,%5         ;"
@@ -88,7 +88,7 @@
   }
 #else
   // Includes a zero-count check.
-  intx temp;
+  intx temp = 0;
   __asm__ volatile("        testl   %6,%6       ;"
                    "        jz      3f          ;"
                    "        cmpl    $32,%6      ;"
@@ -145,7 +145,7 @@
   (void)memmove(to, from, count);
 #else
   // Includes a zero-count check.
-  intx temp;
+  intx temp = 0;
   __asm__ volatile("        testl   %6,%6          ;"
                    "        jz      13f            ;"
                    "        cmpl    %4,%5          ;"
--- a/src/os_cpu/solaris_sparc/vm/vm_version_solaris_sparc.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/os_cpu/solaris_sparc/vm/vm_version_solaris_sparc.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -244,7 +244,6 @@
 bool PICL::open_library() {
   _dl_handle = dlopen("libpicl.so.1", RTLD_LAZY);
   if (_dl_handle == NULL) {
-    warning("PICL (libpicl.so.1) is missing. Performance will not be optimal.");
     return false;
   }
   if (!bind_library_functions()) {
--- a/src/share/vm/c1/c1_Canonicalizer.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/c1/c1_Canonicalizer.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -640,7 +640,7 @@
 
   if (l == r && !lt->is_float_kind()) {
     // pattern: If (a cond a) => simplify to Goto
-    BlockBegin* sux;
+    BlockBegin* sux = NULL;
     switch (x->cond()) {
     case If::eql: sux = x->sux_for(true);  break;
     case If::neq: sux = x->sux_for(false); break;
@@ -648,6 +648,7 @@
     case If::leq: sux = x->sux_for(true);  break;
     case If::gtr: sux = x->sux_for(false); break;
     case If::geq: sux = x->sux_for(true);  break;
+    default: ShouldNotReachHere();
     }
     // If is a safepoint then the debug information should come from the state_before of the If.
     set_canonical(new Goto(sux, x->state_before(), is_safepoint(x, sux)));
@@ -685,7 +686,7 @@
       } else {
         // two successors differ and two successors are the same => simplify to: If (x cmp y)
         // determine new condition & successors
-        If::Condition cond;
+        If::Condition cond = If::eql;
         BlockBegin* tsux = NULL;
         BlockBegin* fsux = NULL;
              if (lss_sux == eql_sux) { cond = If::leq; tsux = lss_sux; fsux = gtr_sux; }
--- a/src/share/vm/c1/c1_GraphBuilder.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/c1/c1_GraphBuilder.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -3973,8 +3973,8 @@
   caller_state->truncate_stack(args_base);
   assert(callee_state->stack_size() == 0, "callee stack must be empty");
 
-  Value lock;
-  BlockBegin* sync_handler;
+  Value lock = NULL;
+  BlockBegin* sync_handler = NULL;
 
   // Inline the locking of the receiver if the callee is synchronized
   if (callee->is_synchronized()) {
--- a/src/share/vm/c1/c1_LIRGenerator.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/c1/c1_LIRGenerator.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -3347,7 +3347,7 @@
 }
 
 void LIRGenerator::increment_event_counter(CodeEmitInfo* info, int bci, bool backedge) {
-  int freq_log;
+  int freq_log = 0;
   int level = compilation()->env()->comp_level();
   if (level == CompLevel_limited_profile) {
     freq_log = (backedge ? Tier2BackedgeNotifyFreqLog : Tier2InvokeNotifyFreqLog);
@@ -3368,7 +3368,7 @@
   assert(level > CompLevel_simple, "Shouldn't be here");
 
   int offset = -1;
-  LIR_Opr counter_holder;
+  LIR_Opr counter_holder = NULL;
   if (level == CompLevel_limited_profile) {
     MethodCounters* counters_adr = method->ensure_method_counters();
     if (counters_adr == NULL) {
--- a/src/share/vm/c1/c1_LIRGenerator.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/c1/c1_LIRGenerator.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -410,7 +410,7 @@
   }
 
   static LIR_Condition lir_cond(If::Condition cond) {
-    LIR_Condition l;
+    LIR_Condition l = lir_cond_unknown;
     switch (cond) {
     case If::eql: l = lir_cond_equal;        break;
     case If::neq: l = lir_cond_notEqual;     break;
@@ -420,6 +420,7 @@
     case If::gtr: l = lir_cond_greater;      break;
     case If::aeq: l = lir_cond_aboveEqual;   break;
     case If::beq: l = lir_cond_belowEqual;   break;
+    default: fatal("You must pass valid If::Condition");
     };
     return l;
   }
--- a/src/share/vm/c1/c1_Runtime1.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/c1/c1_Runtime1.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -312,6 +312,7 @@
   NOT_PRODUCT(_new_instance_slowcase_cnt++;)
 
   assert(klass->is_klass(), "not a class");
+  Handle holder(THREAD, klass->klass_holder()); // keep the klass alive
   instanceKlassHandle h(thread, klass);
   h->check_valid_for_instantiation(true, CHECK);
   // make sure klass is initialized
@@ -347,6 +348,7 @@
   //       anymore after new_objArray() and no GC can happen before.
   //       (This may have to change if this code changes!)
   assert(array_klass->is_klass(), "not a class");
+  Handle holder(THREAD, array_klass->klass_holder()); // keep the klass alive
   Klass* elem_klass = ObjArrayKlass::cast(array_klass)->element_klass();
   objArrayOop obj = oopFactory::new_objArray(elem_klass, length, CHECK);
   thread->set_vm_result(obj);
@@ -363,6 +365,7 @@
 
   assert(klass->is_klass(), "not a class");
   assert(rank >= 1, "rank must be nonzero");
+  Handle holder(THREAD, klass->klass_holder()); // keep the klass alive
   oop obj = ArrayKlass::cast(klass)->multi_allocate(rank, dims, CHECK);
   thread->set_vm_result(obj);
 JRT_END
--- a/src/share/vm/ci/ciObjectFactory.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/ci/ciObjectFactory.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -413,6 +413,7 @@
     metadata_owner_klass = m->as_method()->get_Method()->constants()->pool_holder();
   } else {
     fatal("Not implemented for other types of metadata");
+    return;
   }
 
   oop metadata_holder = metadata_owner_klass->klass_holder();
--- a/src/share/vm/classfile/classFileParser.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/classfile/classFileParser.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -3194,19 +3194,19 @@
 
   // Field size and offset computation
   int nonstatic_field_size = _super_klass() == NULL ? 0 : _super_klass()->nonstatic_field_size();
-  int next_static_oop_offset;
-  int next_static_double_offset;
-  int next_static_word_offset;
-  int next_static_short_offset;
-  int next_static_byte_offset;
-  int next_nonstatic_oop_offset;
-  int next_nonstatic_double_offset;
-  int next_nonstatic_word_offset;
-  int next_nonstatic_short_offset;
-  int next_nonstatic_byte_offset;
-  int first_nonstatic_oop_offset;
-  int next_nonstatic_field_offset;
-  int next_nonstatic_padded_offset;
+  int next_static_oop_offset = 0;
+  int next_static_double_offset = 0;
+  int next_static_word_offset = 0;
+  int next_static_short_offset = 0;
+  int next_static_byte_offset = 0;
+  int next_nonstatic_oop_offset = 0;
+  int next_nonstatic_double_offset = 0;
+  int next_nonstatic_word_offset = 0;
+  int next_nonstatic_short_offset = 0;
+  int next_nonstatic_byte_offset = 0;
+  int first_nonstatic_oop_offset = 0;
+  int next_nonstatic_field_offset = 0;
+  int next_nonstatic_padded_offset = 0;
 
   // Count the contended fields by type.
   //
@@ -3359,14 +3359,14 @@
     ShouldNotReachHere();
   }
 
-  int nonstatic_oop_space_count   = 0;
-  int nonstatic_word_space_count  = 0;
-  int nonstatic_short_space_count = 0;
-  int nonstatic_byte_space_count  = 0;
-  int nonstatic_oop_space_offset;
-  int nonstatic_word_space_offset;
-  int nonstatic_short_space_offset;
-  int nonstatic_byte_space_offset;
+  int nonstatic_oop_space_count    = 0;
+  int nonstatic_word_space_count   = 0;
+  int nonstatic_short_space_count  = 0;
+  int nonstatic_byte_space_count   = 0;
+  int nonstatic_oop_space_offset   = 0;
+  int nonstatic_word_space_offset  = 0;
+  int nonstatic_short_space_offset = 0;
+  int nonstatic_byte_space_offset  = 0;
 
   // Try to squeeze some of the fields into the gaps due to
   // long/double alignment.
@@ -3438,7 +3438,7 @@
     // contended instance fields are handled below
     if (fs.is_contended() && !fs.access_flags().is_static()) continue;
 
-    int real_offset;
+    int real_offset = 0;
     FieldAllocationType atype = (FieldAllocationType) fs.allocation_type();
 
     // pack the rest of the fields
@@ -3571,7 +3571,7 @@
         // handle statics below
         if (fs.access_flags().is_static()) continue;
 
-        int real_offset;
+        int real_offset = 0;
         FieldAllocationType atype = (FieldAllocationType) fs.allocation_type();
 
         switch (atype) {
@@ -3975,6 +3975,11 @@
     // Make sure this is the end of class file stream
     guarantee_property(cfs->at_eos(), "Extra bytes at the end of class file %s", CHECK_(nullHandle));
 
+    if (_class_name == vmSymbols::java_lang_Object()) {
+      check_property(_local_interfaces == Universe::the_empty_klass_array(),
+                     "java.lang.Object cannot implement an interface in class file %s",
+                     CHECK_(nullHandle));
+    }
     // We check super class after class file is parsed and format is checked
     if (super_class_index > 0 && super_klass.is_null()) {
       Symbol*  sk  = cp->klass_name_at(super_class_index);
--- a/src/share/vm/classfile/dictionary.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/classfile/dictionary.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -25,6 +25,7 @@
 #include "precompiled.hpp"
 #include "classfile/dictionary.hpp"
 #include "classfile/systemDictionary.hpp"
+#include "classfile/systemDictionaryShared.hpp"
 #include "memory/iterator.hpp"
 #include "oops/oop.inline.hpp"
 #include "prims/jvmtiRedefineClassesTrace.hpp"
@@ -36,9 +37,16 @@
 DictionaryEntry*  Dictionary::_current_class_entry = NULL;
 int               Dictionary::_current_class_index =    0;
 
+size_t Dictionary::entry_size() {
+  if (DumpSharedSpaces) {
+    return SystemDictionaryShared::dictionary_entry_size();
+  } else {
+    return sizeof(DictionaryEntry);
+  }
+}
 
 Dictionary::Dictionary(int table_size)
-  : TwoOopHashtable<Klass*, mtClass>(table_size, sizeof(DictionaryEntry)) {
+  : TwoOopHashtable<Klass*, mtClass>(table_size, (int)entry_size()) {
   _current_class_index = 0;
   _current_class_entry = NULL;
   _pd_cache_table = new ProtectionDomainCacheTable(defaultProtectionDomainCacheSize);
@@ -47,7 +55,7 @@
 
 Dictionary::Dictionary(int table_size, HashtableBucket<mtClass>* t,
                        int number_of_entries)
-  : TwoOopHashtable<Klass*, mtClass>(table_size, sizeof(DictionaryEntry), t, number_of_entries) {
+  : TwoOopHashtable<Klass*, mtClass>(table_size, (int)entry_size(), t, number_of_entries) {
   _current_class_index = 0;
   _current_class_entry = NULL;
   _pd_cache_table = new ProtectionDomainCacheTable(defaultProtectionDomainCacheSize);
@@ -63,6 +71,9 @@
   entry->set_loader_data(loader_data);
   entry->set_pd_set(NULL);
   assert(klass->oop_is_instance(), "Must be");
+  if (DumpSharedSpaces) {
+    SystemDictionaryShared::init_shared_dictionary_entry(klass, entry);
+  }
   return entry;
 }
 
--- a/src/share/vm/classfile/dictionary.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/classfile/dictionary.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -53,6 +53,7 @@
   DictionaryEntry* get_entry(int index, unsigned int hash,
                              Symbol* name, ClassLoaderData* loader_data);
 
+protected:
   DictionaryEntry* bucket(int i) {
     return (DictionaryEntry*)Hashtable<Klass*, mtClass>::bucket(i);
   }
@@ -66,6 +67,8 @@
     Hashtable<Klass*, mtClass>::add_entry(index, (HashtableEntry<Klass*, mtClass>*)new_entry);
   }
 
+  static size_t entry_size();
+
 public:
   Dictionary(int table_size);
   Dictionary(int table_size, HashtableBucket<mtClass>* t, int number_of_entries);
--- a/src/share/vm/classfile/javaClasses.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/classfile/javaClasses.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -942,7 +942,7 @@
   assert(_group_offset == 0, "offsets should be initialized only once");
 
   Klass* k = SystemDictionary::Thread_klass();
-  compute_offset(_name_offset,      k, vmSymbols::name_name(),      vmSymbols::char_array_signature());
+  compute_offset(_name_offset,      k, vmSymbols::name_name(),      vmSymbols::string_signature());
   compute_offset(_group_offset,     k, vmSymbols::group_name(),     vmSymbols::threadgroup_signature());
   compute_offset(_contextClassLoader_offset, k, vmSymbols::contextClassLoader_name(), vmSymbols::classloader_signature());
   compute_offset(_inheritedAccessControlContext_offset, k, vmSymbols::inheritedAccessControlContext_name(), vmSymbols::accesscontrolcontext_signature());
@@ -972,15 +972,12 @@
 }
 
 
-typeArrayOop java_lang_Thread::name(oop java_thread) {
-  oop name = java_thread->obj_field(_name_offset);
-  assert(name == NULL || (name->is_typeArray() && TypeArrayKlass::cast(name->klass())->element_type() == T_CHAR), "just checking");
-  return typeArrayOop(name);
-}
-
-
-void java_lang_Thread::set_name(oop java_thread, typeArrayOop name) {
-  assert(java_thread->obj_field(_name_offset) == NULL, "name should be NULL");
+oop java_lang_Thread::name(oop java_thread) {
+  return java_thread->obj_field(_name_offset);
+}
+
+
+void java_lang_Thread::set_name(oop java_thread, oop name) {
   java_thread->obj_field_put(_name_offset, name);
 }
 
--- a/src/share/vm/classfile/javaClasses.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/classfile/javaClasses.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -348,8 +348,8 @@
   // Set JavaThread for instance
   static void set_thread(oop java_thread, JavaThread* thread);
   // Name
-  static typeArrayOop name(oop java_thread);
-  static void set_name(oop java_thread, typeArrayOop name);
+  static oop name(oop java_thread);
+  static void set_name(oop java_thread, oop name);
   // Priority
   static ThreadPriority priority(oop java_thread);
   static void set_priority(oop java_thread, ThreadPriority priority);
--- a/src/share/vm/classfile/placeholders.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/classfile/placeholders.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -220,7 +220,7 @@
   }
 
   SeenThread* actionToQueue(PlaceholderTable::classloadAction action) {
-    SeenThread* queuehead;
+    SeenThread* queuehead = NULL;
     switch (action) {
       case PlaceholderTable::LOAD_INSTANCE:
          queuehead = _loadInstanceThreadQ;
--- a/src/share/vm/classfile/stackMapTableFormat.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/classfile/stackMapTableFormat.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2010, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2010, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -203,6 +203,7 @@
   inline bool verify(address start, address end) const;
 
   inline void print_on(outputStream* st, int current_offset) const;
+  inline void print_truncated(outputStream* st, int current_offset) const;
 
   // Create as_xxx and is_xxx methods for the subtypes
 #define FRAME_TYPE_DECL(stackmap_frame_type, arg1, arg2) \
@@ -263,6 +264,10 @@
   void print_on(outputStream* st, int current_offset = -1) const {
     st->print("same_frame(@%d)", offset_delta() + current_offset);
   }
+
+  void print_truncated(outputStream* st, int current_offset = -1) const {
+    print_on(st, current_offset);
+  }
 };
 
 class same_frame_extended : public stack_map_frame {
@@ -309,6 +314,10 @@
   void print_on(outputStream* st, int current_offset = -1) const {
     st->print("same_frame_extended(@%d)", offset_delta() + current_offset);
   }
+
+  void print_truncated(outputStream* st, int current_offset = -1) const {
+    print_on(st, current_offset);
+  }
 };
 
 class same_locals_1_stack_item_frame : public stack_map_frame {
@@ -381,6 +390,11 @@
     types()->print_on(st);
     st->print(")");
   }
+
+  void print_truncated(outputStream* st, int current_offset = -1) const {
+    st->print("same_locals_1_stack_item_frame(@%d), output truncated, Stackmap exceeds table size.",
+              offset_delta() + current_offset);
+  }
 };
 
 class same_locals_1_stack_item_extended : public stack_map_frame {
@@ -446,6 +460,11 @@
     types()->print_on(st);
     st->print(")");
   }
+
+  void print_truncated(outputStream* st, int current_offset = -1) const {
+    st->print("same_locals_1_stack_item_extended(@%d), output truncated, Stackmap exceeds table size.",
+              offset_delta() + current_offset);
+  }
 };
 
 class chop_frame : public stack_map_frame {
@@ -511,6 +530,10 @@
   void print_on(outputStream* st, int current_offset = -1) const {
     st->print("chop_frame(@%d,%d)", offset_delta() + current_offset, chops());
   }
+
+  void print_truncated(outputStream* st, int current_offset = -1) const {
+    print_on(st, current_offset);
+  }
 };
 
 class append_frame : public stack_map_frame {
@@ -619,6 +642,11 @@
     }
     st->print(")");
   }
+
+  void print_truncated(outputStream* st, int current_offset = -1) const {
+    st->print("append_frame(@%d), output truncated, Stackmap exceeds table size.",
+              offset_delta() + current_offset);
+  }
 };
 
 class full_frame : public stack_map_frame {
@@ -784,6 +812,11 @@
     }
     st->print("})");
   }
+
+  void print_truncated(outputStream* st, int current_offset = -1) const {
+    st->print("full_frame(@%d), output truncated, Stackmap exceeds table size.",
+              offset_delta() + current_offset);
+  }
 };
 
 #define VIRTUAL_DISPATCH(stack_frame_type, func_name, args) \
@@ -841,6 +874,10 @@
   FOR_EACH_STACKMAP_FRAME_TYPE(VOID_VIRTUAL_DISPATCH, print_on, (st, offs));
 }
 
+void stack_map_frame::print_truncated(outputStream* st, int offs = -1) const {
+  FOR_EACH_STACKMAP_FRAME_TYPE(VOID_VIRTUAL_DISPATCH, print_truncated, (st, offs));
+}
+
 #undef VIRTUAL_DISPATCH
 #undef VOID_VIRTUAL_DISPATCH
 
--- a/src/share/vm/classfile/systemDictionary.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/classfile/systemDictionary.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -1205,8 +1205,13 @@
 
     if (ik->super() != NULL) {
       Symbol*  cn = ik->super()->name();
-      resolve_super_or_fail(class_name, cn,
-                            class_loader, protection_domain, true, CHECK_(nh));
+      Klass *s = resolve_super_or_fail(class_name, cn,
+                                       class_loader, protection_domain, true, CHECK_(nh));
+      if (s != ik->super()) {
+        // The dynamically resolved super class is not the same as the one we used during dump time,
+        // so we cannot use ik.
+        return nh;
+      }
     }
 
     Array<Klass*>* interfaces = ik->local_interfaces();
@@ -1219,7 +1224,12 @@
       // reinitialized yet (they will be once the interface classes
       // are loaded)
       Symbol*  name  = k->name();
-      resolve_super_or_fail(class_name, name, class_loader, protection_domain, false, CHECK_(nh));
+      Klass* i = resolve_super_or_fail(class_name, name, class_loader, protection_domain, false, CHECK_(nh));
+      if (k != i) {
+        // The dynamically resolved interface class is not the same as the one we used during dump time,
+        // so we cannot use ik.
+        return nh;
+      }
     }
 
     // Adjust methods to recover missing data.  They need addresses for
--- a/src/share/vm/classfile/systemDictionaryShared.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/classfile/systemDictionaryShared.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -26,6 +26,7 @@
 #ifndef SHARE_VM_CLASSFILE_SYSTEMDICTIONARYSHARED_HPP
 #define SHARE_VM_CLASSFILE_SYSTEMDICTIONARYSHARED_HPP
 
+#include "classfile/dictionary.hpp"
 #include "classfile/systemDictionary.hpp"
 
 class SystemDictionaryShared: public SystemDictionary {
@@ -42,6 +43,22 @@
     oop class_loader = loader_data->class_loader();
     return (class_loader == NULL);
   }
+
+  static size_t dictionary_entry_size() {
+    return sizeof(DictionaryEntry);
+  }
+  static void init_shared_dictionary_entry(Klass* k, DictionaryEntry* entry) {}
+
+  // The (non-application) CDS implementation supports only classes in the boot
+  // class loader, which ensures that the verification dependencies are the same
+  // during archive creation time and runtime. Thus we can do the dependency checks
+  // entirely during archive creation time.
+  static void add_verification_dependency(Klass* k, Symbol* accessor_clsname,
+                                          Symbol* target_clsname) {}
+  static void finalize_verification_dependencies() {}
+  static bool check_verification_dependencies(Klass* k, Handle class_loader,
+                                              Handle protection_domain,
+                                              char** message_buffer, TRAPS) {return true;}
 };
 
 #endif // SHARE_VM_CLASSFILE_SYSTEMDICTIONARYSHARED_HPP
--- a/src/share/vm/classfile/verificationType.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/classfile/verificationType.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -24,6 +24,7 @@
 
 #include "precompiled.hpp"
 #include "classfile/symbolTable.hpp"
+#include "classfile/systemDictionaryShared.hpp"
 #include "classfile/verificationType.hpp"
 #include "classfile/verifier.hpp"
 
@@ -73,7 +74,23 @@
       Klass* from_class = SystemDictionary::resolve_or_fail(
           from.name(), Handle(THREAD, klass->class_loader()),
           Handle(THREAD, klass->protection_domain()), true, CHECK_false);
-      return InstanceKlass::cast(from_class)->is_subclass_of(this_class());
+      bool result = InstanceKlass::cast(from_class)->is_subclass_of(this_class());
+      if (result && DumpSharedSpaces) {
+        if (klass()->is_subclass_of(from_class) && klass()->is_subclass_of(this_class())) {
+          // No need to save verification dependency. At run time, <klass> will be
+          // loaded from the archived only if <from_class> and <this_class> are
+          // also loaded from the archive. I.e., all 3 classes are exactly the same
+          // as we saw at archive creation time.
+        } else {
+          // Save the dependency. At run time, we need to check that the condition
+          // from_class->is_subclass_of(this_class() is still true.
+          Symbol* accessor_clsname = from.name();
+          Symbol* target_clsname = this_class()->name();
+          SystemDictionaryShared::add_verification_dependency(klass(),
+                       accessor_clsname, target_clsname);
+        }
+      }
+      return result;
     }
   } else if (is_array() && from.is_array()) {
     VerificationType comp_this = get_component(context, CHECK_false);
--- a/src/share/vm/classfile/verifier.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/classfile/verifier.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -504,8 +504,19 @@
     stack_map_frame* sm_frame = sm_table->entries();
     streamIndentor si2(ss);
     int current_offset = -1;
+    // Subtract two from StackMapAttribute length because the length includes
+    // two bytes for number of table entries.
+    size_t sm_table_space = method->stackmap_data()->length() - 2;
     for (u2 i = 0; i < sm_table->number_of_entries(); ++i) {
       ss->indent();
+      size_t sm_frame_size = sm_frame->size();
+      // If the size of the next stackmap exceeds the length of the entire
+      // stackmap table then print a truncated message and return.
+      if (sm_frame_size > sm_table_space) {
+        sm_frame->print_truncated(ss, current_offset);
+        return;
+      }
+      sm_table_space -= sm_frame_size;
       sm_frame->print_on(ss, current_offset);
       ss->cr();
       current_offset += sm_frame->offset_delta();
@@ -2323,9 +2334,17 @@
       case Bytecodes::_ifnonnull:
         target = bcs.dest();
         if (visited_branches->contains(bci)) {
-          if (bci_stack->is_empty()) return true;
-          // Pop a bytecode starting offset and scan from there.
-          bcs.set_start(bci_stack->pop());
+          if (bci_stack->is_empty()) {
+            if (handler_stack->is_empty()) {
+              return true;
+            } else {
+              // Parse the catch handlers for try blocks containing athrow.
+              bcs.set_start(handler_stack->pop());
+            }
+          } else {
+            // Pop a bytecode starting offset and scan from there.
+            bcs.set_start(bci_stack->pop());
+          }
         } else {
           if (target > bci) { // forward branch
             if (target >= code_length) return false;
@@ -2348,9 +2367,17 @@
       case Bytecodes::_goto_w:
         target = (opcode == Bytecodes::_goto ? bcs.dest() : bcs.dest_w());
         if (visited_branches->contains(bci)) {
-          if (bci_stack->is_empty()) return true;
-          // Been here before, pop new starting offset from stack.
-          bcs.set_start(bci_stack->pop());
+          if (bci_stack->is_empty()) {
+            if (handler_stack->is_empty()) {
+              return true;
+            } else {
+              // Parse the catch handlers for try blocks containing athrow.
+              bcs.set_start(handler_stack->pop());
+            }
+          } else {
+            // Been here before, pop new starting offset from stack.
+            bcs.set_start(bci_stack->pop());
+          }
         } else {
           if (target >= code_length) return false;
           // Continue scanning from the target onward.
--- a/src/share/vm/classfile/vmSymbols.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/classfile/vmSymbols.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -800,10 +800,26 @@
    do_signature(encodeISOArray_signature,                        "([CI[BII)I")                                          \
                                                                                                                         \
   do_class(java_math_BigInteger,                      "java/math/BigInteger")                                           \
-  do_intrinsic(_multiplyToLen,      java_math_BigInteger, multiplyToLen_name, multiplyToLen_signature, F_R)             \
+  do_intrinsic(_multiplyToLen,      java_math_BigInteger, multiplyToLen_name, multiplyToLen_signature, F_S)             \
    do_name(     multiplyToLen_name,                             "multiplyToLen")                                        \
    do_signature(multiplyToLen_signature,                        "([II[II[I)[I")                                         \
                                                                                                                         \
+  do_intrinsic(_squareToLen, java_math_BigInteger, squareToLen_name, squareToLen_signature, F_S)                        \
+   do_name(     squareToLen_name,                             "implSquareToLen")                                        \
+   do_signature(squareToLen_signature,                        "([II[II)[I")                                             \
+                                                                                                                        \
+  do_intrinsic(_mulAdd, java_math_BigInteger, mulAdd_name, mulAdd_signature, F_S)                                       \
+   do_name(     mulAdd_name,                                  "implMulAdd")                                             \
+   do_signature(mulAdd_signature,                             "([I[IIII)I")                                             \
+                                                                                                                        \
+  do_intrinsic(_montgomeryMultiply,      java_math_BigInteger, montgomeryMultiply_name, montgomeryMultiply_signature, F_S) \
+   do_name(     montgomeryMultiply_name,                             "implMontgomeryMultiply")                          \
+   do_signature(montgomeryMultiply_signature,                        "([I[I[IIJ[I)[I")                                  \
+                                                                                                                        \
+  do_intrinsic(_montgomerySquare,      java_math_BigInteger, montgomerySquare_name, montgomerySquare_signature, F_S)    \
+   do_name(     montgomerySquare_name,                             "implMontgomerySquare")                              \
+   do_signature(montgomerySquare_signature,                        "([I[IIJ[I)[I")                                      \
+                                                                                                                        \
   /* java/lang/ref/Reference */                                                                                         \
   do_intrinsic(_Reference_get,            java_lang_ref_Reference, get_name,    void_object_signature, F_R)             \
                                                                                                                         \
--- a/src/share/vm/compiler/oopMap.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/compiler/oopMap.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -74,8 +74,8 @@
 
   // Constructors
   OopMapValue () { set_value(0); set_content_reg(VMRegImpl::Bad()); }
-  OopMapValue (VMReg reg, oop_types t) { set_reg_type(reg,t); }
-  OopMapValue (VMReg reg, oop_types t, VMReg reg2) { set_reg_type(reg,t); set_content_reg(reg2); }
+  OopMapValue (VMReg reg, oop_types t) { set_reg_type(reg, t); set_content_reg(VMRegImpl::Bad()); }
+  OopMapValue (VMReg reg, oop_types t, VMReg reg2) { set_reg_type(reg, t); set_content_reg(reg2); }
   OopMapValue (CompressedReadStream* stream) { read_from(stream); }
 
   // Archiving
@@ -88,7 +88,7 @@
 
   void read_from(CompressedReadStream* stream) {
     set_value(stream->read_int());
-    if(is_callee_saved() || is_derived_oop()) {
+    if (is_callee_saved() || is_derived_oop()) {
       set_content_reg(VMRegImpl::as_VMReg(stream->read_int(), true));
     }
   }
--- a/src/share/vm/gc_implementation/concurrentMarkSweep/concurrentMarkSweepGeneration.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/gc_implementation/concurrentMarkSweep/concurrentMarkSweepGeneration.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -2288,7 +2288,7 @@
   }
 
   // Used for PrintGC
-  size_t prev_used;
+  size_t prev_used = 0;
   if (PrintGC && Verbose) {
     prev_used = _cmsGen->used(); // XXXPERM
   }
@@ -8632,7 +8632,7 @@
 
   HeapWord* const fc_addr = (HeapWord*) fc;
 
-  bool coalesce;
+  bool coalesce = false;
   const size_t left  = pointer_delta(fc_addr, freeFinger());
   const size_t right = chunkSize;
   switch (FLSCoalescePolicy) {
--- a/src/share/vm/gc_implementation/g1/g1CollectedHeap.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/gc_implementation/g1/g1CollectedHeap.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -3996,8 +3996,15 @@
 
     TraceCPUTime tcpu(G1Log::finer(), true, gclog_or_tty);
 
-    uint active_workers = (G1CollectedHeap::use_parallel_gc_threads() ?
-                                workers()->active_workers() : 1);
+    uint active_workers = AdaptiveSizePolicy::calc_active_workers(workers()->total_workers(),
+                                                                  workers()->active_workers(),
+                                                                  Threads::number_of_non_daemon_threads());
+    assert(UseDynamicNumberOfGCThreads ||
+           active_workers == workers()->total_workers(),
+           "If not dynamic should be using all the  workers");
+    workers()->set_active_workers(active_workers);
+
+
     double pause_start_sec = os::elapsedTime();
     g1_policy()->phase_times()->note_gc_start(active_workers, mark_in_progress());
     log_gc_header();
@@ -5768,23 +5775,11 @@
   hot_card_cache->reset_hot_cache_claimed_index();
   hot_card_cache->set_use_cache(false);
 
-  uint n_workers;
-  if (G1CollectedHeap::use_parallel_gc_threads()) {
-    n_workers =
-      AdaptiveSizePolicy::calc_active_workers(workers()->total_workers(),
-                                     workers()->active_workers(),
-                                     Threads::number_of_non_daemon_threads());
+  const uint n_workers = workers()->active_workers();
     assert(UseDynamicNumberOfGCThreads ||
            n_workers == workers()->total_workers(),
            "If not dynamic should be using all the  workers");
-    workers()->set_active_workers(n_workers);
     set_par_threads(n_workers);
-  } else {
-    assert(n_par_threads() == 0,
-           "Should be the original non-parallel value");
-    n_workers = 1;
-  }
-
 
   init_for_evac_failure(NULL);
 
--- a/src/share/vm/gc_implementation/g1/g1GCPhaseTimes.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/gc_implementation/g1/g1GCPhaseTimes.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -154,28 +154,28 @@
     _has_new_data = true;
   }
 
-  double average(){
-    calculate_totals();
+  double average(uint active_threads){
+    calculate_totals(active_threads);
     return _average;
   }
 
-  T sum() {
-    calculate_totals();
+  T sum(uint active_threads) {
+    calculate_totals(active_threads);
     return _sum;
   }
 
-  T minimum() {
-    calculate_totals();
+  T minimum(uint active_threads) {
+    calculate_totals(active_threads);
     return _min;
   }
 
-  T maximum() {
-    calculate_totals();
+  T maximum(uint active_threads) {
+    calculate_totals(active_threads);
     return _max;
   }
 
   void reset() PRODUCT_RETURN;
-  void verify() PRODUCT_RETURN;
+  void verify(uint active_threads) PRODUCT_RETURN;
 
   void set_enabled(bool enabled) { _enabled = enabled; }
 
@@ -183,7 +183,7 @@
 
  private:
 
-  void calculate_totals(){
+  void calculate_totals(uint active_threads){
     if (!_has_new_data) {
       return;
     }
@@ -191,13 +191,14 @@
     _sum = (T)0;
     _min = _data[0];
     _max = _min;
-    for (uint i = 0; i < _length; ++i) {
+    assert(active_threads <= _length, "Wrong number of active threads");
+    for (uint i = 0; i < active_threads; ++i) {
       T val = _data[i];
       _sum += val;
       _min = MIN2(_min, val);
       _max = MAX2(_max, val);
     }
-    _average = (double)_sum / (double)_length;
+    _average = (double)_sum / (double)active_threads;
     _has_new_data = false;
   }
 };
@@ -226,17 +227,18 @@
 }
 
 template <class T>
-void WorkerDataArray<T>::verify() {
+void WorkerDataArray<T>::verify(uint active_threads) {
   if (!_enabled) {
     return;
   }
 
-  for (uint i = 0; i < _length; i++) {
+  assert(active_threads <= _length, "Wrong number of active threads");
+  for (uint i = 0; i < active_threads; i++) {
     assert(_data[i] != WorkerDataArray<T>::uninitialized(),
         err_msg("Invalid data for worker %u in '%s'", i, _title));
   }
   if (_thread_work_items != NULL) {
-    _thread_work_items->verify();
+    _thread_work_items->verify(active_threads);
   }
 }
 
@@ -321,7 +323,7 @@
   }
 
   for (int i = 0; i < GCParPhasesSentinel; i++) {
-    _gc_par_phases[i]->verify();
+    _gc_par_phases[i]->verify(_active_gc_threads);
   }
 }
 
@@ -378,7 +380,7 @@
 
 // return the average time for a phase in milliseconds
 double G1GCPhaseTimes::average_time_ms(GCParPhases phase) {
-  return _gc_par_phases[phase]->average() * 1000.0;
+  return _gc_par_phases[phase]->average(_active_gc_threads) * 1000.0;
 }
 
 double G1GCPhaseTimes::get_time_ms(GCParPhases phase, uint worker_i) {
@@ -386,15 +388,15 @@
 }
 
 double G1GCPhaseTimes::sum_time_ms(GCParPhases phase) {
-  return _gc_par_phases[phase]->sum() * 1000.0;
+  return _gc_par_phases[phase]->sum(_active_gc_threads) * 1000.0;
 }
 
 double G1GCPhaseTimes::min_time_ms(GCParPhases phase) {
-  return _gc_par_phases[phase]->minimum() * 1000.0;
+  return _gc_par_phases[phase]->minimum(_active_gc_threads) * 1000.0;
 }
 
 double G1GCPhaseTimes::max_time_ms(GCParPhases phase) {
-  return _gc_par_phases[phase]->maximum() * 1000.0;
+  return _gc_par_phases[phase]->maximum(_active_gc_threads) * 1000.0;
 }
 
 size_t G1GCPhaseTimes::get_thread_work_item(GCParPhases phase, uint worker_i) {
@@ -404,22 +406,22 @@
 
 size_t G1GCPhaseTimes::sum_thread_work_items(GCParPhases phase) {
   assert(_gc_par_phases[phase]->thread_work_items() != NULL, "No sub count");
-  return _gc_par_phases[phase]->thread_work_items()->sum();
+  return _gc_par_phases[phase]->thread_work_items()->sum(_active_gc_threads);
 }
 
 double G1GCPhaseTimes::average_thread_work_items(GCParPhases phase) {
   assert(_gc_par_phases[phase]->thread_work_items() != NULL, "No sub count");
-  return _gc_par_phases[phase]->thread_work_items()->average();
+  return _gc_par_phases[phase]->thread_work_items()->average(_active_gc_threads);
 }
 
 size_t G1GCPhaseTimes::min_thread_work_items(GCParPhases phase) {
   assert(_gc_par_phases[phase]->thread_work_items() != NULL, "No sub count");
-  return _gc_par_phases[phase]->thread_work_items()->minimum();
+  return _gc_par_phases[phase]->thread_work_items()->minimum(_active_gc_threads);
 }
 
 size_t G1GCPhaseTimes::max_thread_work_items(GCParPhases phase) {
   assert(_gc_par_phases[phase]->thread_work_items() != NULL, "No sub count");
-  return _gc_par_phases[phase]->thread_work_items()->maximum();
+  return _gc_par_phases[phase]->thread_work_items()->maximum(_active_gc_threads);
 }
 
 class G1GCParPhasePrinter : public StackObj {
@@ -455,14 +457,16 @@
   }
 
   void print_time_values(LineBuffer& buf, G1GCPhaseTimes::GCParPhases phase_id, WorkerDataArray<double>* phase) {
-    for (uint i = 0; i < phase->_length; ++i) {
+    uint active_length = _phase_times->_active_gc_threads;
+    for (uint i = 0; i < active_length; ++i) {
       buf.append("  %.1lf", _phase_times->get_time_ms(phase_id, i));
     }
     buf.print_cr();
   }
 
   void print_count_values(LineBuffer& buf, G1GCPhaseTimes::GCParPhases phase_id, WorkerDataArray<size_t>* thread_work_items) {
-    for (uint i = 0; i < thread_work_items->_length; ++i) {
+    uint active_length = _phase_times->_active_gc_threads;
+    for (uint i = 0; i < active_length; ++i) {
       buf.append("  " SIZE_FORMAT, _phase_times->get_thread_work_item(phase_id, i));
     }
     buf.print_cr();
--- a/src/share/vm/gc_implementation/g1/heapRegion.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/gc_implementation/g1/heapRegion.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -794,7 +794,9 @@
                                  "in region "HR_FORMAT,
                                  (void*) obj,
                                  HR_FORMAT_PARAMS(to));
-          obj->print_on(gclog_or_tty);
+          if (obj->is_oop()) {
+            obj->print_on(gclog_or_tty);
+          }
           gclog_or_tty->print_cr("Obj head CTE = %d, field CTE = %d.",
                         cv_obj, cv_field);
           gclog_or_tty->print_cr("----------");
--- a/src/share/vm/gc_implementation/g1/heapRegionRemSet.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/gc_implementation/g1/heapRegionRemSet.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -572,7 +572,7 @@
   assert(_n_fine_entries == _max_fine_entries, "Precondition");
   PerRegionTable* max = NULL;
   jint max_occ = 0;
-  PerRegionTable** max_prev;
+  PerRegionTable** max_prev = NULL;
   size_t max_ind;
 
   size_t i = _fine_eviction_start;
@@ -608,6 +608,7 @@
   }
 
   guarantee(max != NULL, "Since _n_fine_entries > 0");
+  guarantee(max_prev != NULL, "Since max != NULL.");
 
   // Set the corresponding coarse bit.
   size_t max_hrm_index = (size_t) max->hr()->hrm_index();
@@ -1184,7 +1185,7 @@
 
 void HeapRegionRemSet::print_recorded() {
   int cur_evnt = 0;
-  Event cur_evnt_kind;
+  Event cur_evnt_kind = Event_illegal;
   int cur_evnt_ind = 0;
   if (_n_recorded_events > 0) {
     cur_evnt_kind = _recorded_events[cur_evnt];
--- a/src/share/vm/gc_implementation/g1/heapRegionRemSet.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/gc_implementation/g1/heapRegionRemSet.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -232,7 +232,7 @@
 
 public:
   enum Event {
-    Event_EvacStart, Event_EvacEnd, Event_RSUpdateEnd
+    Event_EvacStart, Event_EvacEnd, Event_RSUpdateEnd, Event_illegal
   };
 
 private:
--- a/src/share/vm/gc_implementation/shared/adaptiveSizePolicy.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/gc_implementation/shared/adaptiveSizePolicy.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -168,7 +168,7 @@
 
   if (TraceDynamicGCThreads) {
      gclog_or_tty->print_cr("GCTaskManager::calc_default_active_workers() : "
-       "active_workers(): %d  new_acitve_workers: %d  "
+       "active_workers(): %d  new_active_workers: %d  "
        "prev_active_workers: %d\n"
        " active_workers_by_JT: %d  active_workers_by_heap_size: %d",
        (int) active_workers, (int) new_active_workers, (int) prev_active_workers,
@@ -193,8 +193,9 @@
      (!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);
   }
--- a/src/share/vm/interpreter/bytecodeStream.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/interpreter/bytecodeStream.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -31,12 +31,12 @@
   // set next bytecode position
   address bcp = RawBytecodeStream::bcp();
   address end = method()->code_base() + end_bci();
-  int l = Bytecodes::raw_special_length_at(bcp, end);
-  if (l <= 0 || (_bci + l) > _end_bci) {
+  int len = Bytecodes::raw_special_length_at(bcp, end);
+  // Very large tableswitch or lookupswitch size can cause _next_bci to overflow.
+  if (len <= 0 || (_bci > _end_bci - len) || (_bci - len >= _next_bci)) {
     code = Bytecodes::_illegal;
   } else {
-    _next_bci += l;
-    assert(_bci < _next_bci, "length must be > 0");
+    _next_bci += len;
     // set attributes
     _is_wide = false;
     // check for special (uncommon) cases
--- a/src/share/vm/interpreter/bytecodeStream.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/interpreter/bytecodeStream.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -149,12 +149,15 @@
     code        = Bytecodes::code_or_bp_at(bcp);
 
     // set next bytecode position
-    int l = Bytecodes::length_for(code);
-    if (l > 0 && (_bci + l) <= _end_bci) {
+    int len = Bytecodes::length_for(code);
+    if (len > 0 && (_bci <= _end_bci - len)) {
       assert(code != Bytecodes::_wide && code != Bytecodes::_tableswitch
              && code != Bytecodes::_lookupswitch, "can't be special bytecode");
       _is_wide = false;
-      _next_bci += l;
+      _next_bci += len;
+      if (_next_bci <= _bci) { // Check for integer overflow
+        code = Bytecodes::_illegal;
+      }
       _raw_code = code;
       return code;
     } else {
@@ -203,19 +206,23 @@
       // note that we cannot advance before having the
       // tty bytecode otherwise the stepping is wrong!
       // (carefull: length_for(...) must be used first!)
-      int l = Bytecodes::length_for(code);
-      if (l == 0) l = Bytecodes::length_at(_method(), bcp);
-      _next_bci  += l;
-      assert(_bci < _next_bci, "length must be > 0");
-      // set attributes
-      _is_wide      = false;
-      // check for special (uncommon) cases
-      if (code == Bytecodes::_wide) {
-        raw_code = (Bytecodes::Code)bcp[1];
-        code = raw_code;  // wide BCs are always Java-normal
-        _is_wide = true;
+      int len = Bytecodes::length_for(code);
+      if (len == 0) len = Bytecodes::length_at(_method(), bcp);
+      if (len <= 0 || (_bci > _end_bci - len) || (_bci - len >= _next_bci)) {
+        raw_code = code = Bytecodes::_illegal;
+      } else {
+        _next_bci  += len;
+        assert(_bci < _next_bci, "length must be > 0");
+        // set attributes
+        _is_wide      = false;
+        // check for special (uncommon) cases
+        if (code == Bytecodes::_wide) {
+          raw_code = (Bytecodes::Code)bcp[1];
+          code = raw_code;  // wide BCs are always Java-normal
+          _is_wide = true;
+        }
+        assert(Bytecodes::is_java_code(code), "sanity check");
       }
-      assert(Bytecodes::is_java_code(code), "sanity check");
     }
     _raw_code = raw_code;
     _code = code;
--- a/src/share/vm/interpreter/templateInterpreter.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/interpreter/templateInterpreter.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -528,7 +528,7 @@
   if (StopInterpreterAt > 0)                                     stop_interpreter_at();
   __ verify_FPU(1, t->tos_in());
 #endif // !PRODUCT
-  int step;
+  int step = 0;
   if (!t->does_dispatch()) {
     step = t->is_wide() ? Bytecodes::wide_length_for(t->bytecode()) : Bytecodes::length_for(t->bytecode());
     if (tos_out == ilgl) tos_out = t->tos_out();
--- a/src/share/vm/memory/allocation.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/memory/allocation.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -83,7 +83,7 @@
 }
 
 void* ResourceObj::operator new(size_t size, allocation_type type, MEMFLAGS flags) throw() {
-  address res;
+  address res = NULL;
   switch (type) {
    case C_HEAP:
     res = (address)AllocateHeap(size, flags, CALLER_PC);
@@ -105,8 +105,8 @@
 
 void* ResourceObj::operator new(size_t size, const std::nothrow_t&  nothrow_constant,
     allocation_type type, MEMFLAGS flags) throw() {
-  //should only call this with std::nothrow, use other operator new() otherwise
-  address res;
+  // should only call this with std::nothrow, use other operator new() otherwise
+  address res = NULL;
   switch (type) {
    case C_HEAP:
     res = (address)AllocateHeap(size, flags, CALLER_PC, AllocFailStrategy::RETURN_NULL);
--- a/src/share/vm/memory/metaspaceShared.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/memory/metaspaceShared.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -30,6 +30,7 @@
 #include "classfile/sharedClassUtil.hpp"
 #include "classfile/symbolTable.hpp"
 #include "classfile/systemDictionary.hpp"
+#include "classfile/systemDictionaryShared.hpp"
 #include "code/codeCache.hpp"
 #include "memory/filemap.hpp"
 #include "memory/gcLocker.hpp"
@@ -53,6 +54,7 @@
 bool MetaspaceShared::_check_classes_made_progress;
 bool MetaspaceShared::_has_error_classes;
 bool MetaspaceShared::_archive_loading_failed = false;
+bool MetaspaceShared::_remapped_readwrite = false;
 // Read/write a data stream for restoring/preserving metadata pointers and
 // miscellaneous data from/to the shared archive file.
 
@@ -684,6 +686,10 @@
       exit(1);
     }
   }
+
+  // Copy the dependencies from C_HEAP-alloced GrowableArrays to RO-alloced
+  // Arrays
+  SystemDictionaryShared::finalize_verification_dependencies();
 }
 
 void MetaspaceShared::prepare_for_dumping() {
@@ -1096,6 +1102,7 @@
     if (!mapinfo->remap_shared_readonly_as_readwrite()) {
       return false;
     }
+    _remapped_readwrite = true;
   }
   return true;
 }
--- a/src/share/vm/memory/metaspaceShared.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/memory/metaspaceShared.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -55,6 +55,7 @@
   static bool _check_classes_made_progress;
   static bool _has_error_classes;
   static bool _archive_loading_failed;
+  static bool _remapped_readwrite;
  public:
   enum {
     vtbl_list_size         = 17,   // number of entries in the shared space vtable list.
@@ -123,6 +124,10 @@
   // sharing is enabled. Simply returns true if sharing is not enabled
   // or if the remapping has already been done by a prior call.
   static bool remap_shared_readonly_as_readwrite() NOT_CDS_RETURN_(true);
+  static bool remapped_readwrite() {
+    CDS_ONLY(return _remapped_readwrite);
+    NOT_CDS(return false);
+  }
 
   static void print_shared_spaces();
 
--- a/src/share/vm/memory/universe.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/memory/universe.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -124,6 +124,7 @@
 objArrayOop Universe::_preallocated_out_of_memory_error_array = NULL;
 volatile jint Universe::_preallocated_out_of_memory_error_avail_count = 0;
 bool Universe::_verify_in_progress                    = false;
+long Universe::verify_flags                           = Universe::Verify_All;
 oop Universe::_null_ptr_exception_instance            = NULL;
 oop Universe::_arithmetic_exception_instance          = NULL;
 oop Universe::_virtual_machine_error_instance         = NULL;
@@ -683,6 +684,9 @@
       MetaspaceShared::prepare_for_dumping();
     }
   }
+  if (strlen(VerifySubSet) > 0) {
+    Universe::initialize_verify_flags();
+  }
 
   return JNI_OK;
 }
@@ -1361,6 +1365,53 @@
   st->print_cr("}");
 }
 
+void Universe::initialize_verify_flags() {
+  verify_flags = 0;
+  const char delimiter[] = " ,";
+
+  size_t length = strlen(VerifySubSet);
+  char* subset_list = NEW_C_HEAP_ARRAY(char, length + 1, mtInternal);
+  strncpy(subset_list, VerifySubSet, length + 1);
+
+  char* token = strtok(subset_list, delimiter);
+  while (token != NULL) {
+    if (strcmp(token, "threads") == 0) {
+      verify_flags |= Verify_Threads;
+    } else if (strcmp(token, "heap") == 0) {
+      verify_flags |= Verify_Heap;
+    } else if (strcmp(token, "symbol_table") == 0) {
+      verify_flags |= Verify_SymbolTable;
+    } else if (strcmp(token, "string_table") == 0) {
+      verify_flags |= Verify_StringTable;
+    } else if (strcmp(token, "codecache") == 0) {
+      verify_flags |= Verify_CodeCache;
+    } else if (strcmp(token, "dictionary") == 0) {
+      verify_flags |= Verify_SystemDictionary;
+    } else if (strcmp(token, "classloader_data_graph") == 0) {
+      verify_flags |= Verify_ClassLoaderDataGraph;
+    } else if (strcmp(token, "metaspace") == 0) {
+      verify_flags |= Verify_MetaspaceAux;
+    } else if (strcmp(token, "jni_handles") == 0) {
+      verify_flags |= Verify_JNIHandles;
+    } else if (strcmp(token, "c-heap") == 0) {
+      verify_flags |= Verify_CHeap;
+    } else if (strcmp(token, "codecache_oops") == 0) {
+      verify_flags |= Verify_CodeCacheOops;
+    } else {
+      vm_exit_during_initialization(err_msg("VerifySubSet: \'%s\' memory sub-system is unknown, please correct it", token));
+    }
+    token = strtok(NULL, delimiter);
+  }
+  FREE_C_HEAP_ARRAY(char, subset_list, mtInternal);
+}
+
+bool Universe::should_verify_subset(uint subset) {
+  if (verify_flags & subset) {
+    return true;
+  }
+  return false;
+}
+
 void Universe::verify(VerifyOption option, const char* prefix, bool silent) {
   // The use of _verify_in_progress is a temporary work around for
   // 6320749.  Don't bother with a creating a class to set and clear
@@ -1380,33 +1431,55 @@
 
   if (!silent) gclog_or_tty->print("%s", prefix);
   if (!silent) gclog_or_tty->print("[Verifying ");
-  if (!silent) gclog_or_tty->print("threads ");
-  Threads::verify();
-  if (!silent) gclog_or_tty->print("heap ");
-  heap()->verify(silent, option);
-  if (!silent) gclog_or_tty->print("syms ");
-  SymbolTable::verify();
-  if (!silent) gclog_or_tty->print("strs ");
-  StringTable::verify();
+  if (should_verify_subset(Verify_Threads)) {
+    if (!silent) gclog_or_tty->print("Threads ");
+    Threads::verify();
+  }
+  if (should_verify_subset(Verify_Heap)) {
+    if (!silent) gclog_or_tty->print("Heap ");
+    heap()->verify(silent, option);
+  }
+  if (should_verify_subset(Verify_SymbolTable)) {
+    if (!silent) gclog_or_tty->print("SymbolTable ");
+    SymbolTable::verify();
+  }
+  if (should_verify_subset(Verify_StringTable)) {
+    if (!silent) gclog_or_tty->print("StringTable ");
+    StringTable::verify();
+  }
+  if (should_verify_subset(Verify_CodeCache)) {
   {
     MutexLockerEx mu(CodeCache_lock, Mutex::_no_safepoint_check_flag);
-    if (!silent) gclog_or_tty->print("zone ");
+    if (!silent) gclog_or_tty->print("CodeCache ");
     CodeCache::verify();
   }
-  if (!silent) gclog_or_tty->print("dict ");
-  SystemDictionary::verify();
+  }
+  if (should_verify_subset(Verify_SystemDictionary)) {
+    if (!silent) gclog_or_tty->print("SystemDictionary ");
+    SystemDictionary::verify();
+  }
 #ifndef PRODUCT
-  if (!silent) gclog_or_tty->print("cldg ");
-  ClassLoaderDataGraph::verify();
+  if (should_verify_subset(Verify_ClassLoaderDataGraph)) {
+    if (!silent) gclog_or_tty->print("ClassLoaderDataGraph ");
+    ClassLoaderDataGraph::verify();
+  }
 #endif
-  if (!silent) gclog_or_tty->print("metaspace chunks ");
-  MetaspaceAux::verify_free_chunks();
-  if (!silent) gclog_or_tty->print("hand ");
-  JNIHandles::verify();
-  if (!silent) gclog_or_tty->print("C-heap ");
-  os::check_heap();
-  if (!silent) gclog_or_tty->print("code cache ");
-  CodeCache::verify_oops();
+  if (should_verify_subset(Verify_MetaspaceAux)) {
+    if (!silent) gclog_or_tty->print("MetaspaceAux ");
+    MetaspaceAux::verify_free_chunks();
+  }
+  if (should_verify_subset(Verify_JNIHandles)) {
+    if (!silent) gclog_or_tty->print("JNIHandles ");
+    JNIHandles::verify();
+  }
+  if (should_verify_subset(Verify_CHeap)) {
+    if (!silent) gclog_or_tty->print("C-heap ");
+    os::check_heap();
+  }
+  if (should_verify_subset(Verify_CodeCacheOops)) {
+    if (!silent) gclog_or_tty->print("CodeCache Oops ");
+    CodeCache::verify_oops();
+  }
   if (!silent) gclog_or_tty->print_cr("]");
 
   _verify_in_progress = false;
--- a/src/share/vm/memory/universe.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/memory/universe.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -247,6 +247,7 @@
   static int _verify_count;                           // number of verifies done
   // True during call to verify().  Should only be set/cleared in verify().
   static bool _verify_in_progress;
+  static long verify_flags;
 
   static void compute_verify_oop_data();
 
@@ -425,6 +426,22 @@
   static void init_self_patching_vtbl_list(void** list, int count);
 
   // Debugging
+  enum VERIFY_FLAGS {
+    Verify_Threads = 1,
+    Verify_Heap = 2,
+    Verify_SymbolTable = 4,
+    Verify_StringTable = 8,
+    Verify_CodeCache = 16,
+    Verify_SystemDictionary = 32,
+    Verify_ClassLoaderDataGraph = 64,
+    Verify_MetaspaceAux = 128,
+    Verify_JNIHandles = 256,
+    Verify_CHeap = 512,
+    Verify_CodeCacheOops = 1024,
+    Verify_All = -1
+  };
+  static void initialize_verify_flags();
+  static bool should_verify_subset(uint subset);
   static bool verify_in_progress() { return _verify_in_progress; }
   static void verify(VerifyOption option, const char* prefix, bool silent = VerifySilently);
   static void verify(const char* prefix, bool silent = VerifySilently) {
--- a/src/share/vm/oops/instanceKlass.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/oops/instanceKlass.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -25,6 +25,7 @@
 #include "precompiled.hpp"
 #include "classfile/javaClasses.hpp"
 #include "classfile/systemDictionary.hpp"
+#include "classfile/systemDictionaryShared.hpp"
 #include "classfile/verifier.hpp"
 #include "classfile/vmSymbols.hpp"
 #include "compiler/compileBroker.hpp"
@@ -709,6 +710,16 @@
 
         // also sets rewritten
         this_oop->rewrite_class(CHECK_false);
+      } else if (this_oop()->is_shared()) {
+        ResourceMark rm(THREAD);
+        char* message_buffer; // res-allocated by check_verification_dependencies
+        Handle loader = this_oop()->class_loader();
+        Handle pd     = this_oop()->protection_domain();
+        bool verified = SystemDictionaryShared::check_verification_dependencies(this_oop(),
+                        loader, pd, &message_buffer, THREAD);
+        if (!verified) {
+          THROW_MSG_(vmSymbols::java_lang_VerifyError(), message_buffer, false);
+        }
       }
 
       // relocate jsrs and link methods after they are all rewritten
@@ -718,7 +729,12 @@
       // methods have been rewritten since rewrite may
       // fabricate new Method*s.
       // also does loader constraint checking
-      if (!this_oop()->is_shared()) {
+      //
+      // Initialize_vtable and initialize_itable need to be rerun for
+      // a shared class if the class is not loaded by the NULL classloader.
+      ClassLoaderData * loader_data = this_oop->class_loader_data();
+      if (!(this_oop()->is_shared() &&
+            loader_data->is_the_null_class_loader_data())) {
         ResourceMark rm(THREAD);
         this_oop->vtable()->initialize_vtable(true, CHECK_false);
         this_oop->itable()->initialize_itable(true, CHECK_false);
--- a/src/share/vm/oops/klassVtable.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/oops/klassVtable.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -27,6 +27,7 @@
 #include "classfile/vmSymbols.hpp"
 #include "gc_implementation/shared/markSweep.inline.hpp"
 #include "memory/gcLocker.hpp"
+#include "memory/metaspaceShared.hpp"
 #include "memory/resourceArea.hpp"
 #include "memory/universe.inline.hpp"
 #include "oops/instanceKlass.hpp"
@@ -47,6 +48,10 @@
   return (InstanceKlass*)k;
 }
 
+bool klassVtable::is_preinitialized_vtable() {
+  return _klass->is_shared() && !MetaspaceShared::remapped_readwrite();
+}
+
 
 // this function computes the vtable size (including the size needed for miranda
 // methods) and the number of miranda methods in this class.
@@ -128,6 +133,12 @@
 int klassVtable::initialize_from_super(KlassHandle super) {
   if (super.is_null()) {
     return 0;
+  } else if (is_preinitialized_vtable()) {
+    // A shared class' vtable is preinitialized at dump time. No need to copy
+    // methods from super class for shared class, as that was already done
+    // during archiving time. However, if Jvmti has redefined a class,
+    // copy super class's vtable in case the super class has changed.
+    return super->vtable()->length();
   } else {
     // copy methods from superKlass
     // can't inherit from array class, so must be InstanceKlass
@@ -157,6 +168,8 @@
   KlassHandle super (THREAD, klass()->java_super());
   int nofNewEntries = 0;
 
+  bool is_shared = _klass->is_shared();
+
   if (PrintVtables && !klass()->oop_is_array()) {
     ResourceMark rm(THREAD);
     tty->print_cr("Initializing: %s", _klass->name()->as_C_string());
@@ -169,6 +182,7 @@
 #endif
 
   if (Universe::is_bootstrapping()) {
+    assert(!is_shared, "sanity");
     // just clear everything
     for (int i = 0; i < _length; i++) table()[i].clear();
     return;
@@ -208,6 +222,7 @@
       if (len > 0) {
         Array<int>* def_vtable_indices = NULL;
         if ((def_vtable_indices = ik()->default_vtable_indices()) == NULL) {
+          assert(!is_shared, "shared class def_vtable_indices does not exist");
           def_vtable_indices = ik()->create_new_default_vtable_indices(len, CHECK);
         } else {
           assert(def_vtable_indices->length() == len, "reinit vtable len?");
@@ -222,7 +237,15 @@
           // needs new entry
           if (needs_new_entry) {
             put_method_at(mh(), initialized);
-            def_vtable_indices->at_put(i, initialized); //set vtable index
+            if (is_preinitialized_vtable()) {
+              // At runtime initialize_vtable is rerun for a shared class
+              // (loaded by the non-boot loader) as part of link_class_impl().
+              // The dumptime vtable index should be the same as the runtime index.
+              assert(def_vtable_indices->at(i) == initialized,
+                     "dump time vtable index is different from runtime index");
+            } else {
+              def_vtable_indices->at_put(i, initialized); //set vtable index
+            }
             initialized++;
           }
         }
@@ -365,7 +388,8 @@
   }
 
   // we need a new entry if there is no superclass
-  if (klass->super() == NULL) {
+  Klass* super = klass->super();
+  if (super == NULL) {
     return allocate_new;
   }
 
@@ -394,7 +418,15 @@
 
   Symbol* target_classname = target_klass->name();
   for(int i = 0; i < super_vtable_len; i++) {
-    Method* super_method = method_at(i);
+    Method* super_method;
+    if (is_preinitialized_vtable()) {
+      // If this is a shared class, the vtable is already in the final state (fully
+      // initialized). Need to look at the super's vtable.
+      klassVtable* superVtable = super->vtable();
+      super_method = superVtable->method_at(i);
+    } else {
+      super_method = method_at(i);
+    }
     // Check if method name matches
     if (super_method->name() == name && super_method->signature() == signature) {
 
@@ -458,7 +490,15 @@
          target_method()->set_vtable_index(i);
        } else {
          if (def_vtable_indices != NULL) {
-           def_vtable_indices->at_put(default_index, i);
+           if (is_preinitialized_vtable()) {
+             // At runtime initialize_vtable is rerun as part of link_class_impl()
+             // for a shared class loaded by the non-boot loader.
+             // The dumptime vtable index should be the same as the runtime index.
+             assert(def_vtable_indices->at(default_index) == i,
+                    "dump time vtable index is different from runtime index");
+           } else {
+             def_vtable_indices->at_put(default_index, i);
+           }
          }
          assert(super_method->is_default_method() || super_method->is_overpass()
                 || super_method->is_abstract(), "default override error");
@@ -523,24 +563,33 @@
 }
 
 void klassVtable::put_method_at(Method* m, int index) {
+  if (is_preinitialized_vtable()) {
+    // At runtime initialize_vtable is rerun as part of link_class_impl()
+    // for shared class loaded by the non-boot loader to obtain the loader
+    // constraints based on the runtime classloaders' context. The dumptime
+    // method at the vtable index should be the same as the runtime method.
+    assert(table()[index].method() == m,
+           "archived method is different from the runtime method");
+  } else {
 #ifndef PRODUCT
-  if (PrintVtables && Verbose) {
-    ResourceMark rm;
-    const char* sig = (m != NULL) ? m->name_and_sig_as_C_string() : "<NULL>";
-    tty->print("adding %s at index %d, flags: ", sig, index);
-    if (m != NULL) {
-      m->access_flags().print_on(tty);
-      if (m->is_default_method()) {
-        tty->print("default ");
+    if (PrintVtables && Verbose) {
+      ResourceMark rm;
+      const char* sig = (m != NULL) ? m->name_and_sig_as_C_string() : "<NULL>";
+      tty->print("adding %s at index %d, flags: ", sig, index);
+      if (m != NULL) {
+        m->access_flags().print_on(tty);
+        if (m->is_default_method()) {
+          tty->print("default ");
+        }
+        if (m->is_overpass()) {
+          tty->print("overpass");
+        }
       }
-      if (m->is_overpass()) {
-        tty->print("overpass");
-      }
+      tty->cr();
     }
-    tty->cr();
+#endif
+    table()[index].set(m);
   }
-#endif
-  table()[index].set(m);
 }
 
 // Find out if a method "m" with superclass "super", loader "classloader" and
@@ -971,7 +1020,15 @@
 void itableMethodEntry::initialize(Method* m) {
   if (m == NULL) return;
 
-  _method = m;
+  if (MetaspaceShared::is_in_shared_space((void*)&_method) &&
+     !MetaspaceShared::remapped_readwrite()) {
+    // At runtime initialize_itable is rerun as part of link_class_impl()
+    // for a shared class loaded by the non-boot loader.
+    // The dumptime itable method entry should be the same as the runtime entry.
+    assert(_method == m, "sanity");
+  } else {
+    _method = m;
+  }
 }
 
 klassItable::klassItable(instanceKlassHandle klass) {
@@ -1081,7 +1138,11 @@
         tty->cr();
       }
       if (!m->has_vtable_index()) {
-        assert(m->vtable_index() == Method::pending_itable_index, "set by initialize_vtable");
+        // A shared method could have an initialized itable_index that
+        // is < 0.
+        assert(m->vtable_index() == Method::pending_itable_index ||
+               m->is_shared(),
+               "set by initialize_vtable");
         m->set_itable_index(ime_num);
         // Progress to next itable entry
         ime_num++;
@@ -1277,7 +1338,6 @@
 }
 #endif // INCLUDE_JVMTI
 
-
 // Setup
 class InterfaceVisiterClosure : public StackObj {
  public:
--- a/src/share/vm/oops/klassVtable.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/oops/klassVtable.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -142,6 +142,19 @@
       Array<Klass*>* local_interfaces);
   void verify_against(outputStream* st, klassVtable* vt, int index);
   inline InstanceKlass* ik() const;
+  // When loading a class from CDS archive at run time, and no class redefintion
+  // has happened, it is expected that the class's itable/vtables are
+  // laid out exactly the same way as they had been during dump time.
+  // Therefore, in klassVtable::initialize_[iv]table, we do not layout the
+  // tables again. Instead, we only rerun the process to create/check
+  // the class loader constraints. In non-product builds, we add asserts to
+  // guarantee that the table's layout would be the same as at dump time.
+  //
+  // If JVMTI redefines any class, the read-only shared memory are remapped
+  // as read-write. A shared class' vtable/itable are re-initialized and
+  // might have different layout due to class redefinition of the shared class
+  // or its super types.
+  bool is_preinitialized_vtable();
 };
 
 
--- a/src/share/vm/oops/method.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/oops/method.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -36,6 +36,7 @@
 #include "memory/generation.hpp"
 #include "memory/heapInspection.hpp"
 #include "memory/metadataFactory.hpp"
+#include "memory/metaspaceShared.hpp"
 #include "memory/oopFactory.hpp"
 #include "oops/constMethod.hpp"
 #include "oops/methodData.hpp"
@@ -305,6 +306,33 @@
   unlink_method();
 }
 
+void Method::set_vtable_index(int index) {
+  if (is_shared() && !MetaspaceShared::remapped_readwrite()) {
+    // At runtime initialize_vtable is rerun as part of link_class_impl()
+    // for a shared class loaded by the non-boot loader to obtain the loader
+    // constraints based on the runtime classloaders' context.
+    return; // don't write into the shared class
+  } else {
+    _vtable_index = index;
+  }
+}
+
+void Method::set_itable_index(int index) {
+  if (is_shared() && !MetaspaceShared::remapped_readwrite()) {
+    // At runtime initialize_itable is rerun as part of link_class_impl()
+    // for a shared class loaded by the non-boot loader to obtain the loader
+    // constraints based on the runtime classloaders' context. The dumptime
+    // itable index should be the same as the runtime index.
+    assert(_vtable_index == itable_index_max - index,
+           "archived itable index is different from runtime index");
+    return; // don’t write into the shared class
+  } else {
+    _vtable_index = itable_index_max - index;
+  }
+  assert(valid_itable_index(), "");
+}
+
+
 
 bool Method::was_executed_more_than(int n) {
   // Invocation counter is reset when the Method* is compiled.
--- a/src/share/vm/oops/method.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/oops/method.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -475,12 +475,12 @@
   DEBUG_ONLY(bool valid_vtable_index() const     { return _vtable_index >= nonvirtual_vtable_index; })
   bool has_vtable_index() const                  { return _vtable_index >= 0; }
   int  vtable_index() const                      { return _vtable_index; }
-  void set_vtable_index(int index)               { _vtable_index = index; }
+  void set_vtable_index(int index);
   DEBUG_ONLY(bool valid_itable_index() const     { return _vtable_index <= pending_itable_index; })
   bool has_itable_index() const                  { return _vtable_index <= itable_index_max; }
   int  itable_index() const                      { assert(valid_itable_index(), "");
                                                    return itable_index_max - _vtable_index; }
-  void set_itable_index(int index)               { _vtable_index = itable_index_max - index; assert(valid_itable_index(), ""); }
+  void set_itable_index(int index);
 
   // interpreter entry
   address interpreter_entry() const              { return _i2i_entry; }
--- a/src/share/vm/opto/c2_globals.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/c2_globals.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -662,6 +662,18 @@
   product(bool, UseMultiplyToLenIntrinsic, false,                           \
           "Enables intrinsification of BigInteger.multiplyToLen()")         \
                                                                             \
+  product(bool, UseSquareToLenIntrinsic, false,                             \
+          "Enables intrinsification of BigInteger.squareToLen()")           \
+                                                                            \
+  product(bool, UseMulAddIntrinsic, false,                                  \
+          "Enables intrinsification of BigInteger.mulAdd()")                \
+                                                                            \
+  product(bool, UseMontgomeryMultiplyIntrinsic, false,                      \
+          "Enables intrinsification of BigInteger.montgomeryMultiply()")    \
+                                                                            \
+  product(bool, UseMontgomerySquareIntrinsic, false,                        \
+          "Enables intrinsification of BigInteger.montgomerySquare()")      \
+                                                                            \
   product(bool, UseTypeSpeculation, true,                                   \
           "Speculatively propagate types from profiles")                    \
                                                                             \
--- a/src/share/vm/opto/c2compiler.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/c2compiler.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -49,6 +49,9 @@
 const char* C2Compiler::retry_no_escape_analysis() {
   return "retry without escape analysis";
 }
+const char* C2Compiler::retry_class_loading_during_parsing() {
+  return "retry class loading during parsing";
+}
 bool C2Compiler::init_c2_runtime() {
 
   // Check assumptions used while running ADLC
@@ -115,6 +118,10 @@
 
     // Check result and retry if appropriate.
     if (C.failure_reason() != NULL) {
+      if (C.failure_reason_is(retry_class_loading_during_parsing())) {
+        env->record_failure(C.failure_reason());
+        continue;  // retry
+      }
       if (C.failure_reason_is(retry_no_subsuming_loads())) {
         assert(subsume_loads, "must make progress");
         subsume_loads = false;
--- a/src/share/vm/opto/c2compiler.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/c2compiler.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -51,6 +51,7 @@
   // sentinel value used to trigger backtracking in compile_method().
   static const char* retry_no_subsuming_loads();
   static const char* retry_no_escape_analysis();
+  static const char* retry_class_loading_during_parsing();
 
   // Print compilation timers and statistics
   void print_timers();
--- a/src/share/vm/opto/callGenerator.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/callGenerator.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -658,7 +658,7 @@
                                            &exact_receiver);
 
   SafePointNode* slow_map = NULL;
-  JVMState* slow_jvms;
+  JVMState* slow_jvms = NULL;
   { PreserveJVMState pjvms(&kit);
     kit.set_control(slow_ctl);
     if (!kit.stopped()) {
@@ -829,17 +829,18 @@
           }
         }
         // Cast reference arguments to its type.
-        for (int i = 0; i < signature->count(); i++) {
+        for (int i = 0, j = 0; i < signature->count(); i++) {
           ciType* t = signature->type_at(i);
           if (t->is_klass()) {
-            Node* arg = kit.argument(receiver_skip + i);
+            Node* arg = kit.argument(receiver_skip + j);
             const TypeOopPtr* arg_type = arg->bottom_type()->isa_oopptr();
             const Type*       sig_type = TypeOopPtr::make_from_klass(t->as_klass());
             if (arg_type != NULL && !arg_type->higher_equal(sig_type)) {
               Node* cast_obj = gvn.transform(new (C) CheckCastPPNode(kit.control(), arg, sig_type));
-              kit.set_argument(receiver_skip + i, cast_obj);
+              kit.set_argument(receiver_skip + j, cast_obj);
             }
           }
+          j += t->size();  // long and double take two slots
         }
 
         // Try to get the most accurate receiver type
--- a/src/share/vm/opto/cfgnode.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/cfgnode.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -973,7 +973,7 @@
 #ifdef ASSERT
   // The following logic has been moved into TypeOopPtr::filter.
   const Type* jt = t->join_speculative(_type);
-  if( jt->empty() ) {           // Emptied out???
+  if (jt->empty()) {           // Emptied out???
 
     // Check for evil case of 't' being a class and '_type' expecting an
     // interface.  This can happen because the bytecodes do not contain
@@ -984,14 +984,21 @@
     // be 'I' or 'j/l/O'.  Thus we'll pick 'j/l/O'.  If this then flows
     // into a Phi which "knows" it's an Interface type we'll have to
     // uplift the type.
-    if( !t->empty() && ttip && ttip->is_loaded() && ttip->klass()->is_interface() )
-      { assert(ft == _type, ""); } // Uplift to interface
-    else if( !t->empty() && ttkp && ttkp->is_loaded() && ttkp->klass()->is_interface() )
-      { assert(ft == _type, ""); } // Uplift to interface
-    // Otherwise it's something stupid like non-overlapping int ranges
-    // found on dying counted loops.
-    else
-      { assert(ft == Type::TOP, ""); } // Canonical empty value
+    if (!t->empty() && ttip && ttip->is_loaded() && ttip->klass()->is_interface()) {
+      assert(ft == _type, ""); // Uplift to interface
+    } else if (!t->empty() && ttkp && ttkp->is_loaded() && ttkp->klass()->is_interface()) {
+      assert(ft == _type, ""); // Uplift to interface
+    } else {
+      // We also have to handle 'evil cases' of interface- vs. class-arrays
+      Type::get_arrays_base_elements(jt, _type, NULL, &ttip);
+      if (!t->empty() && ttip != NULL && ttip->is_loaded() && ttip->klass()->is_interface()) {
+          assert(ft == _type, "");   // Uplift to array of interface
+      } else {
+        // Otherwise it's something stupid like non-overlapping int ranges
+        // found on dying counted loops.
+        assert(ft == Type::TOP, ""); // Canonical empty value
+      }
+    }
   }
 
   else {
--- a/src/share/vm/opto/compile.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/compile.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -412,6 +412,13 @@
       remove_macro_node(n);
     }
   }
+  // Remove useless CastII nodes with range check dependency
+  for (int i = range_check_cast_count() - 1; i >= 0; i--) {
+    Node* cast = range_check_cast_node(i);
+    if (!useful.member(cast)) {
+      remove_range_check_cast(cast);
+    }
+  }
   // Remove useless expensive node
   for (int i = C->expensive_count()-1; i >= 0; i--) {
     Node* n = C->expensive_node(i);
@@ -784,7 +791,9 @@
     }
     JVMState* jvms = build_start_state(start(), tf());
     if ((jvms = cg->generate(jvms)) == NULL) {
-      record_method_not_compilable("method parse failed");
+      if (!failure_reason_is(C2Compiler::retry_class_loading_during_parsing())) {
+        record_method_not_compilable("method parse failed");
+      }
       return;
     }
     GraphKit kit(jvms);
@@ -1148,6 +1157,7 @@
   _macro_nodes = new(comp_arena()) GrowableArray<Node*>(comp_arena(), 8,  0, NULL);
   _predicate_opaqs = new(comp_arena()) GrowableArray<Node*>(comp_arena(), 8,  0, NULL);
   _expensive_nodes = new(comp_arena()) GrowableArray<Node*>(comp_arena(), 8,  0, NULL);
+  _range_check_casts = new(comp_arena()) GrowableArray<Node*>(comp_arena(), 8,  0, NULL);
   register_library_intrinsics();
 }
 
@@ -1876,6 +1886,22 @@
   assert(predicate_count()==0, "should be clean!");
 }
 
+void Compile::add_range_check_cast(Node* n) {
+  assert(n->isa_CastII()->has_range_check(), "CastII should have range check dependency");
+  assert(!_range_check_casts->contains(n), "duplicate entry in range check casts");
+  _range_check_casts->append(n);
+}
+
+// Remove all range check dependent CastIINodes.
+void Compile::remove_range_check_casts(PhaseIterGVN &igvn) {
+  for (int i = range_check_cast_count(); i > 0; i--) {
+    Node* cast = range_check_cast_node(i-1);
+    assert(cast->isa_CastII()->has_range_check(), "CastII should have range check dependency");
+    igvn.replace_node(cast, cast->in(1));
+  }
+  assert(range_check_cast_count() == 0, "should be empty");
+}
+
 // StringOpts and late inlining of string methods
 void Compile::inline_string_calls(bool parse_time) {
   {
@@ -2220,6 +2246,12 @@
     PhaseIdealLoop::verify(igvn);
   }
 
+  if (range_check_cast_count() > 0) {
+    // No more loop optimizations. Remove all range check dependent CastIINodes.
+    C->remove_range_check_casts(igvn);
+    igvn.optimize();
+  }
+
   {
     NOT_PRODUCT( TracePhase t2("macroExpand", &_t_macroExpand, TimeCompiler); )
     PhaseMacroExpand  mex(igvn);
@@ -2989,6 +3021,16 @@
 
 #endif
 
+#ifdef ASSERT
+  case Op_CastII:
+    // Verify that all range check dependent CastII nodes were removed.
+    if (n->isa_CastII()->has_range_check()) {
+      n->dump(3);
+      assert(false, "Range check dependent CastII node was not removed");
+    }
+    break;
+#endif
+
   case Op_ModI:
     if (UseDivMod) {
       // Check if a%b and a/b both exist
@@ -3674,7 +3716,7 @@
   MacroAssembler _masm(&cb);
   for (int i = 0; i < _constants.length(); i++) {
     Constant con = _constants.at(i);
-    address constant_addr;
+    address constant_addr = NULL;
     switch (con.type()) {
     case T_LONG:   constant_addr = _masm.long_constant(  con.get_jlong()  ); break;
     case T_FLOAT:  constant_addr = _masm.float_constant( con.get_jfloat() ); break;
@@ -4026,6 +4068,24 @@
   }
 }
 
+// Convert integer value to a narrowed long type dependent on ctrl (for example, a range check)
+Node* Compile::constrained_convI2L(PhaseGVN* phase, Node* value, const TypeInt* itype, Node* ctrl) {
+  if (ctrl != NULL) {
+    // Express control dependency by a CastII node with a narrow type.
+    value = new (phase->C) CastIINode(value, itype, false, true /* range check dependency */);
+    // Make the CastII node dependent on the control input to prevent the narrowed ConvI2L
+    // node from floating above the range check during loop optimizations. Otherwise, the
+    // ConvI2L node may be eliminated independently of the range check, causing the data path
+    // to become TOP while the control path is still there (although it's unreachable).
+    value->set_req(0, ctrl);
+    // Save CastII node to remove it after loop optimizations.
+    phase->C->add_range_check_cast(value);
+    value = phase->transform(value);
+  }
+  const TypeLong* ltype = TypeLong::make(itype->_lo, itype->_hi, itype->_widen);
+  return phase->transform(new (phase->C) ConvI2LNode(value, ltype));
+}
+
 // Auxiliary method to support randomized stressing/fuzzing.
 //
 // This method can be called the arbitrary number of times, with current count
--- a/src/share/vm/opto/compile.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/compile.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -75,6 +75,7 @@
 class JVMState;
 class Type;
 class TypeData;
+class TypeInt;
 class TypePtr;
 class TypeOopPtr;
 class TypeFunc;
@@ -334,6 +335,7 @@
   GrowableArray<Node*>* _macro_nodes;           // List of nodes which need to be expanded before matching.
   GrowableArray<Node*>* _predicate_opaqs;       // List of Opaque1 nodes for the loop predicates.
   GrowableArray<Node*>* _expensive_nodes;       // List of nodes that are expensive to compute and that we'd better not let the GVN freely common
+  GrowableArray<Node*>* _range_check_casts;     // List of CastII nodes with a range check dependency
   ConnectionGraph*      _congraph;
 #ifndef PRODUCT
   IdealGraphPrinter*    _printer;
@@ -669,7 +671,7 @@
   void set_congraph(ConnectionGraph* congraph)  { _congraph = congraph;}
   void add_macro_node(Node * n) {
     //assert(n->is_macro(), "must be a macro node");
-    assert(!_macro_nodes->contains(n), " duplicate entry in expand list");
+    assert(!_macro_nodes->contains(n), "duplicate entry in expand list");
     _macro_nodes->append(n);
   }
   void remove_macro_node(Node * n) {
@@ -689,10 +691,23 @@
     }
   }
   void add_predicate_opaq(Node * n) {
-    assert(!_predicate_opaqs->contains(n), " duplicate entry in predicate opaque1");
+    assert(!_predicate_opaqs->contains(n), "duplicate entry in predicate opaque1");
     assert(_macro_nodes->contains(n), "should have already been in macro list");
     _predicate_opaqs->append(n);
   }
+
+  // Range check dependent CastII nodes that can be removed after loop optimizations
+  void add_range_check_cast(Node* n);
+  void remove_range_check_cast(Node* n) {
+    if (_range_check_casts->contains(n)) {
+      _range_check_casts->remove(n);
+    }
+  }
+  Node* range_check_cast_node(int idx) const { return _range_check_casts->at(idx);  }
+  int   range_check_cast_count()       const { return _range_check_casts->length(); }
+  // Remove all range check dependent CastIINodes.
+  void  remove_range_check_casts(PhaseIterGVN &igvn);
+
   // remove the opaque nodes that protect the predicates so that the unused checks and
   // uncommon traps will be eliminated from the graph.
   void cleanup_loop_predicates(PhaseIterGVN &igvn);
@@ -1201,6 +1216,9 @@
   // Definitions of pd methods
   static void pd_compiler2_init();
 
+  // Convert integer value to a narrowed long type dependent on ctrl (for example, a range check)
+  static Node* constrained_convI2L(PhaseGVN* phase, Node* value, const TypeInt* itype, Node* ctrl);
+
   // Auxiliary method for randomized fuzzing/stressing
   static bool randomized_select(int count);
 };
--- a/src/share/vm/opto/connode.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/connode.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -535,6 +535,9 @@
   if (_carry_dependency) {
     st->print(" carry dependency");
   }
+  if (_range_check_dependency) {
+    st->print(" range check dependency");
+  }
 }
 #endif
 
@@ -994,7 +997,8 @@
   }
 
 #ifdef _LP64
-  // Convert ConvI2L(AddI(x, y)) to AddL(ConvI2L(x), ConvI2L(y)) ,
+  // Convert ConvI2L(AddI(x, y)) to AddL(ConvI2L(x), ConvI2L(y)) or
+  // ConvI2L(CastII(AddI(x, y))) to AddL(ConvI2L(CastII(x)), ConvI2L(CastII(y))),
   // but only if x and y have subranges that cannot cause 32-bit overflow,
   // under the assumption that x+y is in my own subrange this->type().
 
@@ -1018,6 +1022,13 @@
 
   Node* z = in(1);
   int op = z->Opcode();
+  Node* ctrl = NULL;
+  if (op == Op_CastII && z->as_CastII()->has_range_check()) {
+    // Skip CastII node but save control dependency
+    ctrl = z->in(0);
+    z = z->in(1);
+    op = z->Opcode();
+  }
   if (op == Op_AddI || op == Op_SubI) {
     Node* x = z->in(1);
     Node* y = z->in(2);
@@ -1075,9 +1086,10 @@
       rylo = -ryhi;
       ryhi = -rylo0;
     }
-
-    Node* cx = phase->transform( new (phase->C) ConvI2LNode(x, TypeLong::make(rxlo, rxhi, widen)) );
-    Node* cy = phase->transform( new (phase->C) ConvI2LNode(y, TypeLong::make(rylo, ryhi, widen)) );
+    assert(rxlo == (int)rxlo && rxhi == (int)rxhi, "x should not overflow");
+    assert(rylo == (int)rylo && ryhi == (int)ryhi, "y should not overflow");
+    Node* cx = phase->C->constrained_convI2L(phase, x, TypeInt::make(rxlo, rxhi, widen), ctrl);
+    Node* cy = phase->C->constrained_convI2L(phase, y, TypeInt::make(rylo, ryhi, widen), ctrl);
     switch (op) {
     case Op_AddI:  return new (phase->C) AddLNode(cx, cy);
     case Op_SubI:  return new (phase->C) SubLNode(cx, cy);
--- a/src/share/vm/opto/connode.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/connode.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -244,19 +244,31 @@
   private:
   // Can this node be removed post CCP or does it carry a required dependency?
   const bool _carry_dependency;
+  // Is this node dependent on a range check?
+  const bool _range_check_dependency;
 
   protected:
   virtual uint cmp( const Node &n ) const;
   virtual uint size_of() const;
 
 public:
-  CastIINode(Node *n, const Type *t, bool carry_dependency = false)
-    : ConstraintCastNode(n,t), _carry_dependency(carry_dependency) {}
+  CastIINode(Node *n, const Type *t, bool carry_dependency = false, bool range_check_dependency = false)
+    : ConstraintCastNode(n,t), _carry_dependency(carry_dependency), _range_check_dependency(range_check_dependency) {
+    init_class_id(Class_CastII);
+  }
   virtual int Opcode() const;
   virtual uint ideal_reg() const { return Op_RegI; }
   virtual Node *Identity( PhaseTransform *phase );
   virtual const Type *Value( PhaseTransform *phase ) const;
   virtual Node *Ideal_DU_postCCP( PhaseCCP * );
+  const bool has_range_check() {
+ #ifdef _LP64
+     return _range_check_dependency;
+ #else
+     assert(!_range_check_dependency, "Should not have range check dependency");
+     return false;
+ #endif
+   }
 #ifndef PRODUCT
   virtual void dump_spec(outputStream *st) const;
 #endif
--- a/src/share/vm/opto/escape.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/escape.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -958,8 +958,12 @@
                   strcmp(call->as_CallLeaf()->_name, "sha256_implCompressMB") == 0 ||
                   strcmp(call->as_CallLeaf()->_name, "sha512_implCompress") == 0 ||
                   strcmp(call->as_CallLeaf()->_name, "sha512_implCompressMB") == 0 ||
-                  strcmp(call->as_CallLeaf()->_name, "multiplyToLen") == 0)
-                  ))) {
+                  strcmp(call->as_CallLeaf()->_name, "multiplyToLen") == 0 ||
+                  strcmp(call->as_CallLeaf()->_name, "squareToLen") == 0 ||
+                  strcmp(call->as_CallLeaf()->_name, "mulAdd") == 0 ||
+                  strcmp(call->as_CallLeaf()->_name, "montgomery_multiply") == 0 ||
+                  strcmp(call->as_CallLeaf()->_name, "montgomery_square") == 0)
+                 ))) {
             call->dump();
             fatal(err_msg_res("EA unexpected CallLeaf %s", call->as_CallLeaf()->_name));
           }
--- a/src/share/vm/opto/generateOptoStub.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/generateOptoStub.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -273,7 +273,7 @@
 
   //-----------------------------
   // If this is a normal subroutine return, issue the return and be done.
-  Node *ret;
+  Node *ret = NULL;
   switch( is_fancy_jump ) {
   case 0:                       // Make a return instruction
     // Return to caller, free any space for return address
--- a/src/share/vm/opto/graphKit.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/graphKit.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1645,7 +1645,7 @@
 
 //-------------------------array_element_address-------------------------
 Node* GraphKit::array_element_address(Node* ary, Node* idx, BasicType elembt,
-                                      const TypeInt* sizetype) {
+                                      const TypeInt* sizetype, Node* ctrl) {
   uint shift  = exact_log2(type2aelembytes(elembt));
   uint header = arrayOopDesc::base_offset_in_bytes(elembt);
 
@@ -1670,9 +1670,9 @@
   // number.  (The prior range check has ensured this.)
   // This assertion is used by ConvI2LNode::Ideal.
   int index_max = max_jint - 1;  // array size is max_jint, index is one less
-  if (sizetype != NULL)  index_max = sizetype->_hi - 1;
-  const TypeLong* lidxtype = TypeLong::make(CONST64(0), index_max, Type::WidenMax);
-  idx = _gvn.transform( new (C) ConvI2LNode(idx, lidxtype) );
+  if (sizetype != NULL) index_max = sizetype->_hi - 1;
+  const TypeInt* iidxtype = TypeInt::make(0, index_max, Type::WidenMax);
+  idx = C->constrained_convI2L(&_gvn, idx, iidxtype, ctrl);
 #endif
   Node* scale = _gvn.transform( new (C) LShiftXNode(idx, intcon(shift)) );
   return basic_plus_adr(ary, base, scale);
@@ -3491,10 +3491,6 @@
 
   Node* initial_slow_cmp  = _gvn.transform( new (C) CmpUNode( length, intcon( fast_size_limit ) ) );
   Node* initial_slow_test = _gvn.transform( new (C) BoolNode( initial_slow_cmp, BoolTest::gt ) );
-  if (initial_slow_test->is_Bool()) {
-    // Hide it behind a CMoveI, or else PhaseIdealLoop::split_up will get sick.
-    initial_slow_test = initial_slow_test->as_Bool()->as_int_value(&_gvn);
-  }
 
   // --- Size Computation ---
   // array_size = round_to_heap(array_header + (length << elem_shift));
@@ -3540,13 +3536,35 @@
   Node* lengthx = ConvI2X(length);
   Node* headerx = ConvI2X(header_size);
 #ifdef _LP64
-  { const TypeLong* tllen = _gvn.find_long_type(lengthx);
-    if (tllen != NULL && tllen->_lo < 0) {
+  { const TypeInt* tilen = _gvn.find_int_type(length);
+    if (tilen != NULL && tilen->_lo < 0) {
       // Add a manual constraint to a positive range.  Cf. array_element_address.
-      jlong size_max = arrayOopDesc::max_array_length(T_BYTE);
-      if (size_max > tllen->_hi)  size_max = tllen->_hi;
-      const TypeLong* tlcon = TypeLong::make(CONST64(0), size_max, Type::WidenMin);
-      lengthx = _gvn.transform( new (C) ConvI2LNode(length, tlcon));
+      jlong size_max = fast_size_limit;
+      if (size_max > tilen->_hi)  size_max = tilen->_hi;
+      const TypeInt* tlcon = TypeInt::make(0, size_max, Type::WidenMin);
+
+      // Only do a narrow I2L conversion if the range check passed.
+      IfNode* iff = new (C) IfNode(control(), initial_slow_test, PROB_MIN, COUNT_UNKNOWN);
+      _gvn.transform(iff);
+      RegionNode* region = new (C) RegionNode(3);
+      _gvn.set_type(region, Type::CONTROL);
+      lengthx = new (C) PhiNode(region, TypeLong::LONG);
+      _gvn.set_type(lengthx, TypeLong::LONG);
+
+      // Range check passed. Use ConvI2L node with narrow type.
+      Node* passed = IfFalse(iff);
+      region->init_req(1, passed);
+      // Make I2L conversion control dependent to prevent it from
+      // floating above the range check during loop optimizations.
+      lengthx->init_req(1, C->constrained_convI2L(&_gvn, length, tlcon, passed));
+
+      // Range check failed. Use ConvI2L with wide type because length may be invalid.
+      region->init_req(2, IfTrue(iff));
+      lengthx->init_req(2, ConvI2X(length));
+
+      set_control(region);
+      record_for_igvn(region);
+      record_for_igvn(lengthx);
     }
   }
 #endif
@@ -3577,6 +3595,11 @@
   Node *mem = reset_memory();
   set_all_memory(mem); // Create new memory state
 
+  if (initial_slow_test->is_Bool()) {
+    // Hide it behind a CMoveI, or else PhaseIdealLoop::split_up will get sick.
+    initial_slow_test = initial_slow_test->as_Bool()->as_int_value(&_gvn);
+  }
+
   // Create the AllocateArrayNode and its result projections
   AllocateArrayNode* alloc
     = new (C) AllocateArrayNode(C, AllocateArrayNode::alloc_type(TypeInt::INT),
--- a/src/share/vm/opto/graphKit.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/graphKit.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -626,7 +626,9 @@
   // Return addressing for an array element.
   Node* array_element_address(Node* ary, Node* idx, BasicType elembt,
                               // Optional constraint on the array size:
-                              const TypeInt* sizetype = NULL);
+                              const TypeInt* sizetype = NULL,
+                              // Optional control dependency (for example, on range check)
+                              Node* ctrl = NULL);
 
   // Return a load of array element at idx.
   Node* load_array_element(Node* ctl, Node* ary, Node* idx, const TypeAryPtr* arytype);
--- a/src/share/vm/opto/lcm.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/lcm.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -675,7 +675,7 @@
   block->insert_node(proj, node_cnt++);
 
   // Select the right register save policy.
-  const char * save_policy;
+  const char *save_policy = NULL;
   switch (op) {
     case Op_CallRuntime:
     case Op_CallLeaf:
--- a/src/share/vm/opto/library_call.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/library_call.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -324,6 +324,10 @@
   bool inline_updateBytesCRC32();
   bool inline_updateByteBufferCRC32();
   bool inline_multiplyToLen();
+  bool inline_squareToLen();
+  bool inline_mulAdd();
+  bool inline_montgomeryMultiply();
+  bool inline_montgomerySquare();
 
   bool inline_profileBoolean();
 };
@@ -527,6 +531,21 @@
     if (!UseMultiplyToLenIntrinsic) return NULL;
     break;
 
+  case vmIntrinsics::_squareToLen:
+    if (!UseSquareToLenIntrinsic) return NULL;
+    break;
+
+  case vmIntrinsics::_mulAdd:
+    if (!UseMulAddIntrinsic) return NULL;
+    break;
+
+  case vmIntrinsics::_montgomeryMultiply:
+     if (!UseMontgomeryMultiplyIntrinsic) return NULL;
+    break;
+  case vmIntrinsics::_montgomerySquare:
+     if (!UseMontgomerySquareIntrinsic) return NULL;
+    break;
+
   case vmIntrinsics::_cipherBlockChaining_encryptAESCrypt:
   case vmIntrinsics::_cipherBlockChaining_decryptAESCrypt:
     if (!UseAESIntrinsics) return NULL;
@@ -927,6 +946,17 @@
   case vmIntrinsics::_multiplyToLen:
     return inline_multiplyToLen();
 
+  case vmIntrinsics::_squareToLen:
+    return inline_squareToLen();
+
+  case vmIntrinsics::_mulAdd:
+    return inline_mulAdd();
+
+  case vmIntrinsics::_montgomeryMultiply:
+    return inline_montgomeryMultiply();
+  case vmIntrinsics::_montgomerySquare:
+    return inline_montgomerySquare();
+
   case vmIntrinsics::_encodeISOArray:
     return inline_encodeISOArray();
 
@@ -1619,7 +1649,7 @@
 // public static double Math.log10(double)
 bool LibraryCallKit::inline_math(vmIntrinsics::ID id) {
   Node* arg = round_double_node(argument(0));
-  Node* n;
+  Node* n = NULL;
   switch (id) {
   case vmIntrinsics::_dabs:   n = new (C) AbsDNode(                arg);  break;
   case vmIntrinsics::_dsqrt:  n = new (C) SqrtDNode(C, control(),  arg);  break;
@@ -2360,7 +2390,7 @@
 // inline long       Long.reverseBytes(long)
 bool LibraryCallKit::inline_number_methods(vmIntrinsics::ID id) {
   Node* arg = argument(0);
-  Node* n;
+  Node* n = NULL;
   switch (id) {
   case vmIntrinsics::_numberOfLeadingZeros_i:   n = new (C) CountLeadingZerosINode( arg);  break;
   case vmIntrinsics::_numberOfLeadingZeros_l:   n = new (C) CountLeadingZerosLNode( arg);  break;
@@ -2955,7 +2985,7 @@
 
   // For now, we handle only those cases that actually exist: ints,
   // longs, and Object. Adding others should be straightforward.
-  Node* load_store;
+  Node* load_store = NULL;
   switch(type) {
   case T_INT:
     if (kind == LS_xadd) {
@@ -3875,7 +3905,7 @@
   Node* end               = is_copyOfRange? argument(2): argument(1);
   Node* array_type_mirror = is_copyOfRange? argument(3): argument(2);
 
-  Node* newcopy;
+  Node* newcopy = NULL;
 
   // Set the original stack and the reexecute bit for the interpreter to reexecute
   // the bytecode that invokes Arrays.copyOf if deoptimization happens.
@@ -4263,7 +4293,7 @@
 
 bool LibraryCallKit::inline_fp_conversions(vmIntrinsics::ID id) {
   Node* arg = argument(0);
-  Node* result;
+  Node* result = NULL;
 
   switch (id) {
   case vmIntrinsics::_floatToRawIntBits:    result = new (C) MoveF2INode(arg);  break;
@@ -5767,11 +5797,12 @@
 
   assert(callee()->signature()->size() == 5, "multiplyToLen has 5 parameters");
 
-  Node* x    = argument(1);
-  Node* xlen = argument(2);
-  Node* y    = argument(3);
-  Node* ylen = argument(4);
-  Node* z    = argument(5);
+  // no receiver because it is a static method
+  Node* x    = argument(0);
+  Node* xlen = argument(1);
+  Node* y    = argument(2);
+  Node* ylen = argument(3);
+  Node* z    = argument(4);
 
   const Type* x_type = x->Value(&_gvn);
   const Type* y_type = y->Value(&_gvn);
@@ -5856,6 +5887,215 @@
   return true;
 }
 
+//-------------inline_squareToLen------------------------------------
+bool LibraryCallKit::inline_squareToLen() {
+  assert(UseSquareToLenIntrinsic, "not implementated on this platform");
+
+  address stubAddr = StubRoutines::squareToLen();
+  if (stubAddr == NULL) {
+    return false; // Intrinsic's stub is not implemented on this platform
+  }
+  const char* stubName = "squareToLen";
+
+  assert(callee()->signature()->size() == 4, "implSquareToLen has 4 parameters");
+
+  Node* x    = argument(0);
+  Node* len  = argument(1);
+  Node* z    = argument(2);
+  Node* zlen = argument(3);
+
+  const Type* x_type = x->Value(&_gvn);
+  const Type* z_type = z->Value(&_gvn);
+  const TypeAryPtr* top_x = x_type->isa_aryptr();
+  const TypeAryPtr* top_z = z_type->isa_aryptr();
+  if (top_x  == NULL || top_x->klass()  == NULL ||
+      top_z  == NULL || top_z->klass()  == NULL) {
+    // failed array check
+    return false;
+  }
+
+  BasicType x_elem = x_type->isa_aryptr()->klass()->as_array_klass()->element_type()->basic_type();
+  BasicType z_elem = z_type->isa_aryptr()->klass()->as_array_klass()->element_type()->basic_type();
+  if (x_elem != T_INT || z_elem != T_INT) {
+    return false;
+  }
+
+
+  Node* x_start = array_element_address(x, intcon(0), x_elem);
+  Node* z_start = array_element_address(z, intcon(0), z_elem);
+
+  Node*  call = make_runtime_call(RC_LEAF|RC_NO_FP,
+                                  OptoRuntime::squareToLen_Type(),
+                                  stubAddr, stubName, TypePtr::BOTTOM,
+                                  x_start, len, z_start, zlen);
+
+  set_result(z);
+  return true;
+}
+
+//-------------inline_mulAdd------------------------------------------
+bool LibraryCallKit::inline_mulAdd() {
+  assert(UseMulAddIntrinsic, "not implementated on this platform");
+
+  address stubAddr = StubRoutines::mulAdd();
+  if (stubAddr == NULL) {
+    return false; // Intrinsic's stub is not implemented on this platform
+  }
+  const char* stubName = "mulAdd";
+
+  assert(callee()->signature()->size() == 5, "mulAdd has 5 parameters");
+
+  Node* out      = argument(0);
+  Node* in       = argument(1);
+  Node* offset   = argument(2);
+  Node* len      = argument(3);
+  Node* k        = argument(4);
+
+  const Type* out_type = out->Value(&_gvn);
+  const Type* in_type = in->Value(&_gvn);
+  const TypeAryPtr* top_out = out_type->isa_aryptr();
+  const TypeAryPtr* top_in = in_type->isa_aryptr();
+  if (top_out  == NULL || top_out->klass()  == NULL ||
+      top_in == NULL || top_in->klass() == NULL) {
+    // failed array check
+    return false;
+  }
+
+  BasicType out_elem = out_type->isa_aryptr()->klass()->as_array_klass()->element_type()->basic_type();
+  BasicType in_elem = in_type->isa_aryptr()->klass()->as_array_klass()->element_type()->basic_type();
+  if (out_elem != T_INT || in_elem != T_INT) {
+    return false;
+  }
+
+  Node* outlen = load_array_length(out);
+  Node* new_offset = _gvn.transform(new (C) SubINode(outlen, offset));
+  Node* out_start = array_element_address(out, intcon(0), out_elem);
+  Node* in_start = array_element_address(in, intcon(0), in_elem);
+
+  Node*  call = make_runtime_call(RC_LEAF|RC_NO_FP,
+                                  OptoRuntime::mulAdd_Type(),
+                                  stubAddr, stubName, TypePtr::BOTTOM,
+                                  out_start,in_start, new_offset, len, k);
+  Node* result = _gvn.transform(new (C) ProjNode(call, TypeFunc::Parms));
+  set_result(result);
+  return true;
+}
+
+//-------------inline_montgomeryMultiply-----------------------------------
+bool LibraryCallKit::inline_montgomeryMultiply() {
+  address stubAddr = StubRoutines::montgomeryMultiply();
+  if (stubAddr == NULL) {
+    return false; // Intrinsic's stub is not implemented on this platform
+  }
+
+  assert(UseMontgomeryMultiplyIntrinsic, "not implemented on this platform");
+  const char* stubName = "montgomery_square";
+
+  assert(callee()->signature()->size() == 7, "montgomeryMultiply has 7 parameters");
+
+  Node* a    = argument(0);
+  Node* b    = argument(1);
+  Node* n    = argument(2);
+  Node* len  = argument(3);
+  Node* inv  = argument(4);
+  Node* m    = argument(6);
+
+  const Type* a_type = a->Value(&_gvn);
+  const TypeAryPtr* top_a = a_type->isa_aryptr();
+  const Type* b_type = b->Value(&_gvn);
+  const TypeAryPtr* top_b = b_type->isa_aryptr();
+  const Type* n_type = a->Value(&_gvn);
+  const TypeAryPtr* top_n = n_type->isa_aryptr();
+  const Type* m_type = a->Value(&_gvn);
+  const TypeAryPtr* top_m = m_type->isa_aryptr();
+  if (top_a  == NULL || top_a->klass()  == NULL ||
+      top_b == NULL || top_b->klass()  == NULL ||
+      top_n == NULL || top_n->klass()  == NULL ||
+      top_m == NULL || top_m->klass()  == NULL) {
+    // failed array check
+    return false;
+  }
+
+  BasicType a_elem = a_type->isa_aryptr()->klass()->as_array_klass()->element_type()->basic_type();
+  BasicType b_elem = b_type->isa_aryptr()->klass()->as_array_klass()->element_type()->basic_type();
+  BasicType n_elem = n_type->isa_aryptr()->klass()->as_array_klass()->element_type()->basic_type();
+  BasicType m_elem = m_type->isa_aryptr()->klass()->as_array_klass()->element_type()->basic_type();
+  if (a_elem != T_INT || b_elem != T_INT || n_elem != T_INT || m_elem != T_INT) {
+    return false;
+  }
+
+  // Make the call
+  {
+    Node* a_start = array_element_address(a, intcon(0), a_elem);
+    Node* b_start = array_element_address(b, intcon(0), b_elem);
+    Node* n_start = array_element_address(n, intcon(0), n_elem);
+    Node* m_start = array_element_address(m, intcon(0), m_elem);
+
+    Node* call = make_runtime_call(RC_LEAF,
+                                   OptoRuntime::montgomeryMultiply_Type(),
+                                   stubAddr, stubName, TypePtr::BOTTOM,
+                                   a_start, b_start, n_start, len, inv, top(),
+                                   m_start);
+    set_result(m);
+  }
+
+  return true;
+}
+
+bool LibraryCallKit::inline_montgomerySquare() {
+  address stubAddr = StubRoutines::montgomerySquare();
+  if (stubAddr == NULL) {
+    return false; // Intrinsic's stub is not implemented on this platform
+  }
+
+  assert(UseMontgomerySquareIntrinsic, "not implemented on this platform");
+  const char* stubName = "montgomery_square";
+
+  assert(callee()->signature()->size() == 6, "montgomerySquare has 6 parameters");
+
+  Node* a    = argument(0);
+  Node* n    = argument(1);
+  Node* len  = argument(2);
+  Node* inv  = argument(3);
+  Node* m    = argument(5);
+
+  const Type* a_type = a->Value(&_gvn);
+  const TypeAryPtr* top_a = a_type->isa_aryptr();
+  const Type* n_type = a->Value(&_gvn);
+  const TypeAryPtr* top_n = n_type->isa_aryptr();
+  const Type* m_type = a->Value(&_gvn);
+  const TypeAryPtr* top_m = m_type->isa_aryptr();
+  if (top_a  == NULL || top_a->klass()  == NULL ||
+      top_n == NULL || top_n->klass()  == NULL ||
+      top_m == NULL || top_m->klass()  == NULL) {
+    // failed array check
+    return false;
+  }
+
+  BasicType a_elem = a_type->isa_aryptr()->klass()->as_array_klass()->element_type()->basic_type();
+  BasicType n_elem = n_type->isa_aryptr()->klass()->as_array_klass()->element_type()->basic_type();
+  BasicType m_elem = m_type->isa_aryptr()->klass()->as_array_klass()->element_type()->basic_type();
+  if (a_elem != T_INT || n_elem != T_INT || m_elem != T_INT) {
+    return false;
+  }
+
+  // Make the call
+  {
+    Node* a_start = array_element_address(a, intcon(0), a_elem);
+    Node* n_start = array_element_address(n, intcon(0), n_elem);
+    Node* m_start = array_element_address(m, intcon(0), m_elem);
+
+    Node* call = make_runtime_call(RC_LEAF,
+                                   OptoRuntime::montgomerySquare_Type(),
+                                   stubAddr, stubName, TypePtr::BOTTOM,
+                                   a_start, n_start, len, inv, top(),
+                                   m_start);
+    set_result(m);
+  }
+
+  return true;
+}
+
 
 /**
  * Calculate CRC32 for byte.
@@ -6054,7 +6294,7 @@
 
 //------------------------------inline_aescrypt_Block-----------------------
 bool LibraryCallKit::inline_aescrypt_Block(vmIntrinsics::ID id) {
-  address stubAddr;
+  address stubAddr = NULL;
   const char *stubName;
   assert(UseAES, "need AES instruction support");
 
@@ -6120,8 +6360,8 @@
 
 //------------------------------inline_cipherBlockChaining_AESCrypt-----------------------
 bool LibraryCallKit::inline_cipherBlockChaining_AESCrypt(vmIntrinsics::ID id) {
-  address stubAddr;
-  const char *stubName;
+  address stubAddr = NULL;
+  const char *stubName = NULL;
 
   assert(UseAES, "need AES instruction support");
 
--- a/src/share/vm/opto/loopTransform.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/loopTransform.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -2438,7 +2438,7 @@
 
 //=============================================================================
 // Process all the loops in the loop tree and replace any fill
-// patterns with an intrisc version.
+// patterns with an intrinsic version.
 bool PhaseIdealLoop::do_intrinsify_fill() {
   bool changed = false;
   for (LoopTreeIterator iter(_ltree_root); !iter.done(); iter.next()) {
@@ -2536,8 +2536,9 @@
   }
 
   // Make sure the address expression can be handled.  It should be
-  // head->phi * elsize + con.  head->phi might have a ConvI2L.
+  // head->phi * elsize + con.  head->phi might have a ConvI2L(CastII()).
   Node* elements[4];
+  Node* cast = NULL;
   Node* conv = NULL;
   bool found_index = false;
   int count = store->in(MemNode::Address)->as_AddP()->unpack_offsets(elements, ARRAY_SIZE(elements));
@@ -2552,6 +2553,12 @@
         conv = value;
         value = value->in(1);
       }
+      if (value->Opcode() == Op_CastII &&
+          value->as_CastII()->has_range_check()) {
+        // Skip range check dependent CastII nodes
+        cast = value;
+        value = value->in(1);
+      }
 #endif
       if (value != head->phi()) {
         msg = "unhandled shift in address";
@@ -2564,9 +2571,16 @@
         }
       }
     } else if (n->Opcode() == Op_ConvI2L && conv == NULL) {
-      if (n->in(1) == head->phi()) {
+      conv = n;
+      n = n->in(1);
+      if (n->Opcode() == Op_CastII &&
+          n->as_CastII()->has_range_check()) {
+        // Skip range check dependent CastII nodes
+        cast = n;
+        n = n->in(1);
+      }
+      if (n == head->phi()) {
         found_index = true;
-        conv = n;
       } else {
         msg = "unhandled input to ConvI2L";
       }
@@ -2625,6 +2639,7 @@
   // Address elements are ok
   if (con)   ok.set(con->_idx);
   if (shift) ok.set(shift->_idx);
+  if (cast)  ok.set(cast->_idx);
   if (conv)  ok.set(conv->_idx);
 
   for (uint i = 0; msg == NULL && i < lpt->_body.size(); i++) {
@@ -2821,7 +2836,7 @@
   // state of the loop.  It's safe in this case to replace it with the
   // result_mem.
   _igvn.replace_node(store->in(MemNode::Memory), result_mem);
-  _igvn.replace_node(exit, result_ctrl);
+  lazy_replace(exit, result_ctrl);
   _igvn.replace_node(store, result_mem);
   // Any uses the increment outside of the loop become the loop limit.
   _igvn.replace_node(head->incr(), head->limit());
--- a/src/share/vm/opto/loopnode.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/loopnode.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -750,8 +750,8 @@
     set_loop(iff2, get_loop(iffalse));
 
     // Lazy update of 'get_ctrl' mechanism.
-    lazy_replace_proj( iffalse, iff2 );
-    lazy_replace_proj( iftrue,  ift2 );
+    lazy_replace(iffalse, iff2);
+    lazy_replace(iftrue,  ift2);
 
     // Swap names
     iffalse = iff2;
--- a/src/share/vm/opto/loopnode.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/loopnode.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -660,13 +660,18 @@
   }
 
 private:
-  Node *get_ctrl_no_update( Node *i ) const {
+  Node *get_ctrl_no_update_helper(Node *i) const {
+    assert(has_ctrl(i), "should be control, not loop");
+    return (Node*)(((intptr_t)_nodes[i->_idx]) & ~1);
+  }
+
+  Node *get_ctrl_no_update(Node *i) const {
     assert( has_ctrl(i), "" );
-    Node *n = (Node*)(((intptr_t)_nodes[i->_idx]) & ~1);
+    Node *n = get_ctrl_no_update_helper(i);
     if (!n->in(0)) {
       // Skip dead CFG nodes
       do {
-        n = (Node*)(((intptr_t)_nodes[n->_idx]) & ~1);
+        n = get_ctrl_no_update_helper(n);
       } while (!n->in(0));
       n = find_non_split_ctrl(n);
     }
@@ -688,22 +693,15 @@
   // from old_node to new_node to support the lazy update.  Reference
   // replaces loop reference, since that is not needed for dead node.
 public:
-  void lazy_update( Node *old_node, Node *new_node ) {
-    assert( old_node != new_node, "no cycles please" );
-    //old_node->set_req( 1, new_node /*NO DU INFO*/ );
-    // Nodes always have DU info now, so re-use the side array slot
-    // for this node to provide the forwarding pointer.
-    _nodes.map( old_node->_idx, (Node*)((intptr_t)new_node + 1) );
+  void lazy_update(Node *old_node, Node *new_node) {
+    assert(old_node != new_node, "no cycles please");
+    // Re-use the side array slot for this node to provide the
+    // forwarding pointer.
+    _nodes.map(old_node->_idx, (Node*)((intptr_t)new_node + 1));
   }
-  void lazy_replace( Node *old_node, Node *new_node ) {
-    _igvn.replace_node( old_node, new_node );
-    lazy_update( old_node, new_node );
-  }
-  void lazy_replace_proj( Node *old_node, Node *new_node ) {
-    assert( old_node->req() == 1, "use this for Projs" );
-    _igvn.hash_delete(old_node); // Must hash-delete before hacking edges
-    old_node->add_req( NULL );
-    lazy_replace( old_node, new_node );
+  void lazy_replace(Node *old_node, Node *new_node) {
+    _igvn.replace_node(old_node, new_node);
+    lazy_update(old_node, new_node);
   }
 
 private:
--- a/src/share/vm/opto/loopopts.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/loopopts.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -43,6 +43,14 @@
     return NULL;
   }
 
+  // Splitting range check CastIIs through a loop induction Phi can
+  // cause new Phis to be created that are left unrelated to the loop
+  // induction Phi and prevent optimizations (vectorization)
+  if (n->Opcode() == Op_CastII && n->as_CastII()->has_range_check() &&
+      region->is_CountedLoop() && n->in(1) == region->as_CountedLoop()->phi()) {
+    return NULL;
+  }
+
   int wins = 0;
   assert(!n->is_CFG(), "");
   assert(region->is_Region(), "");
@@ -772,6 +780,9 @@
 #ifdef _LP64
         if (m->Opcode() == Op_ConvI2L)
           return false;
+        if (m->is_CastII() && m->isa_CastII()->has_range_check()) {
+          return false;
+        }
 #endif
       }
     }
--- a/src/share/vm/opto/macro.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/macro.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -693,10 +693,10 @@
   ciKlass* klass = NULL;
   ciInstanceKlass* iklass = NULL;
   int nfields = 0;
-  int array_base;
-  int element_size;
-  BasicType basic_elem_type;
-  ciType* elem_type;
+  int array_base = 0;
+  int element_size = 0;
+  BasicType basic_elem_type = T_ILLEGAL;
+  ciType* elem_type = NULL;
 
   Node* res = alloc->result_cast();
   assert(res == NULL || res->is_CheckCastPP(), "unexpected AllocateNode result");
@@ -1177,10 +1177,10 @@
   // We need a Region and corresponding Phi's to merge the slow-path and fast-path results.
   // they will not be used if "always_slow" is set
   enum { slow_result_path = 1, fast_result_path = 2 };
-  Node *result_region;
-  Node *result_phi_rawmem;
-  Node *result_phi_rawoop;
-  Node *result_phi_i_o;
+  Node *result_region = NULL;
+  Node *result_phi_rawmem = NULL;
+  Node *result_phi_rawoop = NULL;
+  Node *result_phi_i_o = NULL;
 
   // The initial slow comparison is a size check, the comparison
   // we want to do is a BoolTest::gt
--- a/src/share/vm/opto/node.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/node.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -529,6 +529,11 @@
     C->add_macro_node(n);
   if (is_expensive())
     C->add_expensive_node(n);
+  // If the cloned node is a range check dependent CastII, add it to the list.
+  CastIINode* cast = n->isa_CastII();
+  if (cast != NULL && cast->has_range_check()) {
+    C->add_range_check_cast(cast);
+  }
 
   n->set_idx(C->next_unique()); // Get new unique index as well
   debug_only( n->verify_construction() );
@@ -657,6 +662,11 @@
   if (is_expensive()) {
     compile->remove_expensive_node(this);
   }
+  CastIINode* cast = isa_CastII();
+  if (cast != NULL && cast->has_range_check()) {
+    compile->remove_range_check_cast(cast);
+  }
+
   if (is_SafePoint()) {
     as_SafePoint()->delete_replaced_nodes();
   }
@@ -1352,6 +1362,10 @@
       if (dead->is_expensive()) {
         igvn->C->remove_expensive_node(dead);
       }
+      CastIINode* cast = dead->isa_CastII();
+      if (cast != NULL && cast->has_range_check()) {
+        igvn->C->remove_range_check_cast(cast);
+      }
       igvn->C->record_dead_node(dead->_idx);
       // Kill all inputs to the dead guy
       for (uint i=0; i < dead->req(); i++) {
--- a/src/share/vm/opto/node.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/node.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -54,6 +54,7 @@
 class CatchNode;
 class CatchProjNode;
 class CheckCastPPNode;
+class CastIINode;
 class ClearArrayNode;
 class CmpNode;
 class CodeBuffer;
@@ -603,6 +604,7 @@
     DEFINE_CLASS_ID(Type,  Node, 2)
       DEFINE_CLASS_ID(Phi,   Type, 0)
       DEFINE_CLASS_ID(ConstraintCast, Type, 1)
+        DEFINE_CLASS_ID(CastII, ConstraintCast, 0)
       DEFINE_CLASS_ID(CheckCastPP, Type, 2)
       DEFINE_CLASS_ID(CMove, Type, 3)
       DEFINE_CLASS_ID(SafePointScalarObject, Type, 4)
@@ -727,6 +729,7 @@
   DEFINE_CLASS_QUERY(Catch)
   DEFINE_CLASS_QUERY(CatchProj)
   DEFINE_CLASS_QUERY(CheckCastPP)
+  DEFINE_CLASS_QUERY(CastII)
   DEFINE_CLASS_QUERY(ConstraintCast)
   DEFINE_CLASS_QUERY(ClearArray)
   DEFINE_CLASS_QUERY(CMove)
--- a/src/share/vm/opto/parse1.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/parse1.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -27,6 +27,7 @@
 #include "interpreter/linkResolver.hpp"
 #include "oops/method.hpp"
 #include "opto/addnode.hpp"
+#include "opto/c2compiler.hpp"
 #include "opto/idealGraphPrinter.hpp"
 #include "opto/locknode.hpp"
 #include "opto/memnode.hpp"
@@ -105,7 +106,7 @@
 
   // Very similar to LoadNode::make, except we handle un-aligned longs and
   // doubles on Sparc.  Intel can handle them just fine directly.
-  Node *l;
+  Node *l = NULL;
   switch (bt) {                // Signature is flattened
   case T_INT:     l = new (C) LoadINode(ctl, mem, adr, TypeRawPtr::BOTTOM, TypeInt::INT,        MemNode::unordered); break;
   case T_FLOAT:   l = new (C) LoadFNode(ctl, mem, adr, TypeRawPtr::BOTTOM, Type::FLOAT,         MemNode::unordered); break;
@@ -988,7 +989,23 @@
   if (tf()->range()->cnt() > TypeFunc::Parms) {
     const Type* ret_type = tf()->range()->field_at(TypeFunc::Parms);
     Node*       ret_phi  = _gvn.transform( _exits.argument(0) );
-    assert(_exits.control()->is_top() || !_gvn.type(ret_phi)->empty(), "return value must be well defined");
+    if (!_exits.control()->is_top() && _gvn.type(ret_phi)->empty()) {
+      // In case of concurrent class loading, the type we set for the
+      // ret_phi in build_exits() may have been too optimistic and the
+      // ret_phi may be top now.
+      // Otherwise, we've encountered an error and have to mark the method as
+      // not compilable. Just using an assertion instead would be dangerous
+      // as this could lead to an infinite compile loop in non-debug builds.
+      {
+        MutexLockerEx ml(Compile_lock, Mutex::_no_safepoint_check_flag);
+        if (C->env()->system_dictionary_modification_counter_changed()) {
+          C->record_failure(C2Compiler::retry_class_loading_during_parsing());
+        } else {
+          C->record_method_not_compilable("Can't determine return type.");
+        }
+      }
+      return;
+    }
     if (ret_type->isa_int()) {
       BasicType ret_bt = method()->return_type()->basic_type();
       ret_phi = mask_int_value(ret_phi, ret_bt, &_gvn);
@@ -1897,7 +1914,7 @@
   // Now use a Phi here for merging
   assert(!nocreate, "Cannot build a phi for a block already parsed.");
   const JVMState* jvms = map->jvms();
-  const Type* t;
+  const Type* t = NULL;
   if (jvms->is_loc(idx)) {
     t = block()->local_type_at(idx - jvms->locoff());
   } else if (jvms->is_stk(idx)) {
@@ -2116,15 +2133,24 @@
     // here.
     Node* phi = _exits.argument(0);
     const TypeInstPtr *tr = phi->bottom_type()->isa_instptr();
-    if( tr && tr->klass()->is_loaded() &&
-        tr->klass()->is_interface() ) {
+    if (tr && tr->klass()->is_loaded() &&
+        tr->klass()->is_interface()) {
       const TypeInstPtr *tp = value->bottom_type()->isa_instptr();
       if (tp && tp->klass()->is_loaded() &&
           !tp->klass()->is_interface()) {
         // sharpen the type eagerly; this eases certain assert checking
         if (tp->higher_equal(TypeInstPtr::NOTNULL))
           tr = tr->join_speculative(TypeInstPtr::NOTNULL)->is_instptr();
-        value = _gvn.transform(new (C) CheckCastPPNode(0,value,tr));
+        value = _gvn.transform(new (C) CheckCastPPNode(0, value, tr));
+      }
+    } else {
+      // Also handle returns of oop-arrays to an arrays-of-interface return
+      const TypeInstPtr* phi_tip;
+      const TypeInstPtr* val_tip;
+      Type::get_arrays_base_elements(phi->bottom_type(), value->bottom_type(), &phi_tip, &val_tip);
+      if (phi_tip != NULL && phi_tip->is_loaded() && phi_tip->klass()->is_interface() &&
+          val_tip != NULL && val_tip->is_loaded() && !val_tip->klass()->is_interface()) {
+         value = _gvn.transform(new (C) CheckCastPPNode(0, value, phi->bottom_type()));
       }
     }
     phi->add_req(value);
--- a/src/share/vm/opto/parse2.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/parse2.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -158,7 +158,9 @@
   // Check for always knowing you are throwing a range-check exception
   if (stopped())  return top();
 
-  Node* ptr = array_element_address(ary, idx, type, sizetype);
+  // Make array address computation control dependent to prevent it
+  // from floating above the range check during loop optimizations.
+  Node* ptr = array_element_address(ary, idx, type, sizetype, control());
 
   if (result2 != NULL)  *result2 = elemtype;
 
@@ -461,9 +463,12 @@
 #ifdef _LP64
   // Clean the 32-bit int into a real 64-bit offset.
   // Otherwise, the jint value 0 might turn into an offset of 0x0800000000.
-  const TypeLong* lkeytype = TypeLong::make(CONST64(0), num_cases-1, Type::WidenMin);
-  key_val       = _gvn.transform( new (C) ConvI2LNode(key_val, lkeytype) );
+  const TypeInt* ikeytype = TypeInt::make(0, num_cases-1, Type::WidenMin);
+  // Make I2L conversion control dependent to prevent it from
+  // floating above the range check during loop optimizations.
+  key_val = C->constrained_convI2L(&_gvn, key_val, ikeytype, control());
 #endif
+
   // Shift the value by wordsize so we have an index into the table, rather
   // than a switch value
   Node *shiftWord = _gvn.MakeConX(wordSize);
--- a/src/share/vm/opto/phaseX.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/phaseX.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1339,6 +1339,10 @@
       if (dead->is_expensive()) {
         C->remove_expensive_node(dead);
       }
+      CastIINode* cast = dead->isa_CastII();
+      if (cast != NULL && cast->has_range_check()) {
+        C->remove_range_check_cast(cast);
+      }
     }
   } // while (_stack.is_nonempty())
 }
--- a/src/share/vm/opto/runtime.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/runtime.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -231,22 +231,17 @@
 
   // These checks are cheap to make and support reflective allocation.
   int lh = klass->layout_helper();
-  if (Klass::layout_helper_needs_slow_path(lh)
-      || !InstanceKlass::cast(klass)->is_initialized()) {
-    KlassHandle kh(THREAD, klass);
-    kh->check_valid_for_instantiation(false, THREAD);
+  if (Klass::layout_helper_needs_slow_path(lh) || !InstanceKlass::cast(klass)->is_initialized()) {
+    Handle holder(THREAD, klass->klass_holder()); // keep the klass alive
+    klass->check_valid_for_instantiation(false, THREAD);
     if (!HAS_PENDING_EXCEPTION) {
-      InstanceKlass::cast(kh())->initialize(THREAD);
-    }
-    if (!HAS_PENDING_EXCEPTION) {
-      klass = kh();
-    } else {
-      klass = NULL;
+      InstanceKlass::cast(klass)->initialize(THREAD);
     }
   }
 
-  if (klass != NULL) {
+  if (!HAS_PENDING_EXCEPTION) {
     // Scavenge and allocate an instance.
+    Handle holder(THREAD, klass->klass_holder()); // keep the klass alive
     oop result = InstanceKlass::cast(klass)->allocate_instance(THREAD);
     thread->set_vm_result(result);
 
@@ -286,6 +281,7 @@
     // Although the oopFactory likes to work with the elem_type,
     // the compiler prefers the array_type, since it must already have
     // that latter value in hand for the fast path.
+    Handle holder(THREAD, array_type->klass_holder()); // keep the array klass alive
     Klass* elem_type = ObjArrayKlass::cast(array_type)->element_klass();
     result = oopFactory::new_objArray(elem_type, len, THREAD);
   }
@@ -364,6 +360,7 @@
   jint dims[2];
   dims[0] = len1;
   dims[1] = len2;
+  Handle holder(THREAD, elem_type->klass_holder()); // keep the klass alive
   oop obj = ArrayKlass::cast(elem_type)->multi_allocate(2, dims, THREAD);
   deoptimize_caller_frame(thread, HAS_PENDING_EXCEPTION);
   thread->set_vm_result(obj);
@@ -380,6 +377,7 @@
   dims[0] = len1;
   dims[1] = len2;
   dims[2] = len3;
+  Handle holder(THREAD, elem_type->klass_holder()); // keep the klass alive
   oop obj = ArrayKlass::cast(elem_type)->multi_allocate(3, dims, THREAD);
   deoptimize_caller_frame(thread, HAS_PENDING_EXCEPTION);
   thread->set_vm_result(obj);
@@ -397,6 +395,7 @@
   dims[1] = len2;
   dims[2] = len3;
   dims[3] = len4;
+  Handle holder(THREAD, elem_type->klass_holder()); // keep the klass alive
   oop obj = ArrayKlass::cast(elem_type)->multi_allocate(4, dims, THREAD);
   deoptimize_caller_frame(thread, HAS_PENDING_EXCEPTION);
   thread->set_vm_result(obj);
@@ -415,6 +414,7 @@
   dims[2] = len3;
   dims[3] = len4;
   dims[4] = len5;
+  Handle holder(THREAD, elem_type->klass_holder()); // keep the klass alive
   oop obj = ArrayKlass::cast(elem_type)->multi_allocate(5, dims, THREAD);
   deoptimize_caller_frame(thread, HAS_PENDING_EXCEPTION);
   thread->set_vm_result(obj);
@@ -432,6 +432,7 @@
   jint *c_dims = NEW_RESOURCE_ARRAY(jint, len);
   Copy::conjoint_jints_atomic(j_dims, c_dims, len);
 
+  Handle holder(THREAD, elem_type->klass_holder()); // keep the klass alive
   oop obj = ArrayKlass::cast(elem_type)->multi_allocate(len, c_dims, THREAD);
   deoptimize_caller_frame(thread, HAS_PENDING_EXCEPTION);
   thread->set_vm_result(obj);
@@ -956,6 +957,94 @@
   return TypeFunc::make(domain, range);
 }
 
+const TypeFunc* OptoRuntime::squareToLen_Type() {
+  // create input type (domain)
+  int num_args      = 4;
+  int argcnt = num_args;
+  const Type** fields = TypeTuple::fields(argcnt);
+  int argp = TypeFunc::Parms;
+  fields[argp++] = TypePtr::NOTNULL;    // x
+  fields[argp++] = TypeInt::INT;        // len
+  fields[argp++] = TypePtr::NOTNULL;    // z
+  fields[argp++] = TypeInt::INT;        // zlen
+  assert(argp == TypeFunc::Parms+argcnt, "correct decoding");
+  const TypeTuple* domain = TypeTuple::make(TypeFunc::Parms+argcnt, fields);
+
+  // no result type needed
+  fields = TypeTuple::fields(1);
+  fields[TypeFunc::Parms+0] = NULL;
+  const TypeTuple* range = TypeTuple::make(TypeFunc::Parms, fields);
+  return TypeFunc::make(domain, range);
+}
+
+// for mulAdd calls, 2 pointers and 3 ints, returning int
+const TypeFunc* OptoRuntime::mulAdd_Type() {
+  // create input type (domain)
+  int num_args      = 5;
+  int argcnt = num_args;
+  const Type** fields = TypeTuple::fields(argcnt);
+  int argp = TypeFunc::Parms;
+  fields[argp++] = TypePtr::NOTNULL;    // out
+  fields[argp++] = TypePtr::NOTNULL;    // in
+  fields[argp++] = TypeInt::INT;        // offset
+  fields[argp++] = TypeInt::INT;        // len
+  fields[argp++] = TypeInt::INT;        // k
+  assert(argp == TypeFunc::Parms+argcnt, "correct decoding");
+  const TypeTuple* domain = TypeTuple::make(TypeFunc::Parms+argcnt, fields);
+
+  // returning carry (int)
+  fields = TypeTuple::fields(1);
+  fields[TypeFunc::Parms+0] = TypeInt::INT;
+  const TypeTuple* range = TypeTuple::make(TypeFunc::Parms+1, fields);
+  return TypeFunc::make(domain, range);
+}
+
+const TypeFunc* OptoRuntime::montgomeryMultiply_Type() {
+  // create input type (domain)
+  int num_args      = 7;
+  int argcnt = num_args;
+  const Type** fields = TypeTuple::fields(argcnt);
+  int argp = TypeFunc::Parms;
+  fields[argp++] = TypePtr::NOTNULL;    // a
+  fields[argp++] = TypePtr::NOTNULL;    // b
+  fields[argp++] = TypePtr::NOTNULL;    // n
+  fields[argp++] = TypeInt::INT;        // len
+  fields[argp++] = TypeLong::LONG;      // inv
+  fields[argp++] = Type::HALF;
+  fields[argp++] = TypePtr::NOTNULL;    // result
+  assert(argp == TypeFunc::Parms+argcnt, "correct decoding");
+  const TypeTuple* domain = TypeTuple::make(TypeFunc::Parms+argcnt, fields);
+
+  // result type needed
+  fields = TypeTuple::fields(1);
+  fields[TypeFunc::Parms+0] = TypePtr::NOTNULL;
+
+  const TypeTuple* range = TypeTuple::make(TypeFunc::Parms, fields);
+  return TypeFunc::make(domain, range);
+}
+
+const TypeFunc* OptoRuntime::montgomerySquare_Type() {
+  // create input type (domain)
+  int num_args      = 6;
+  int argcnt = num_args;
+  const Type** fields = TypeTuple::fields(argcnt);
+  int argp = TypeFunc::Parms;
+  fields[argp++] = TypePtr::NOTNULL;    // a
+  fields[argp++] = TypePtr::NOTNULL;    // n
+  fields[argp++] = TypeInt::INT;        // len
+  fields[argp++] = TypeLong::LONG;      // inv
+  fields[argp++] = Type::HALF;
+  fields[argp++] = TypePtr::NOTNULL;    // result
+  assert(argp == TypeFunc::Parms+argcnt, "correct decoding");
+  const TypeTuple* domain = TypeTuple::make(TypeFunc::Parms+argcnt, fields);
+
+  // result type needed
+  fields = TypeTuple::fields(1);
+  fields[TypeFunc::Parms+0] = TypePtr::NOTNULL;
+
+  const TypeTuple* range = TypeTuple::make(TypeFunc::Parms, fields);
+  return TypeFunc::make(domain, range);
+}
 
 
 //------------- Interpreter state access for on stack replacement
--- a/src/share/vm/opto/runtime.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/runtime.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -305,6 +305,12 @@
 
   static const TypeFunc* multiplyToLen_Type();
 
+  static const TypeFunc* squareToLen_Type();
+
+  static const TypeFunc* mulAdd_Type();
+  static const TypeFunc* montgomeryMultiply_Type();
+  static const TypeFunc* montgomerySquare_Type();
+
   static const TypeFunc* updateBytesCRC32_Type();
 
   // leaf on stack replacement interpreter accessor types
--- a/src/share/vm/opto/split_if.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/split_if.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -451,8 +451,8 @@
 
   // Replace both uses of 'new_iff' with Regions merging True/False
   // paths.  This makes 'new_iff' go dead.
-  Node *old_false, *old_true;
-  Node *new_false, *new_true;
+  Node *old_false = NULL, *old_true = NULL;
+  Node *new_false = NULL, *new_true = NULL;
   for (DUIterator_Last j2min, j2 = iff->last_outs(j2min); j2 >= j2min; --j2) {
     Node *ifp = iff->last_out(j2);
     assert( ifp->Opcode() == Op_IfFalse || ifp->Opcode() == Op_IfTrue, "" );
@@ -472,7 +472,7 @@
 
     // Replace in the graph with lazy-update mechanism
     new_iff->set_req(0, new_iff); // hook self so it does not go dead
-    lazy_replace_proj( ifp, ifpx );
+    lazy_replace(ifp, ifpx);
     new_iff->set_req(0, region);
 
     // Record bits for later xforms
--- a/src/share/vm/opto/stringopts.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/stringopts.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2009, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2009, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -1640,6 +1640,17 @@
       kit.store_String_length(kit.control(), result, length);
     }
     kit.store_String_value(kit.control(), result, char_array);
+
+    // Do not let stores that initialize this object be reordered with
+    // a subsequent store that would make this object accessible by
+    // other threads.
+    // Record what AllocateNode this StoreStore protects so that
+    // escape analysis can go from the MemBarStoreStoreNode to the
+    // AllocateNode and eliminate the MemBarStoreStoreNode if possible
+    // based on the escape status of the AllocateNode.
+    AllocateNode* alloc = AllocateNode::Ideal_allocation(result, _gvn);
+    assert(alloc != NULL, "should be newly allocated");
+    kit.insert_mem_bar(Op_MemBarStoreStore, alloc->proj_out(AllocateNode::RawAddress));
   } else {
     result = C->top();
   }
--- a/src/share/vm/opto/superword.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/superword.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -2388,6 +2388,11 @@
       return true;
     }
   } else if (opc == Op_ConvI2L) {
+    if (n->in(1)->Opcode() == Op_CastII &&
+        n->in(1)->as_CastII()->has_range_check()) {
+      // Skip range check dependent CastII nodes
+      n = n->in(1);
+    }
     if (scaled_iv_plus_offset(n->in(1))) {
       return true;
     }
--- a/src/share/vm/opto/type.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/type.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -149,6 +149,33 @@
   return bt;
 }
 
+// For two instance arrays of same dimension, return the base element types.
+// Otherwise or if the arrays have different dimensions, return NULL.
+void Type::get_arrays_base_elements(const Type *a1, const Type *a2,
+                                    const TypeInstPtr **e1, const TypeInstPtr **e2) {
+
+  if (e1) *e1 = NULL;
+  if (e2) *e2 = NULL;
+  const TypeAryPtr* a1tap = (a1 == NULL) ? NULL : a1->isa_aryptr();
+  const TypeAryPtr* a2tap = (a2 == NULL) ? NULL : a2->isa_aryptr();
+
+  if (a1tap != NULL && a2tap != NULL) {
+    // Handle multidimensional arrays
+    const TypePtr* a1tp = a1tap->elem()->make_ptr();
+    const TypePtr* a2tp = a2tap->elem()->make_ptr();
+    while (a1tp && a1tp->isa_aryptr() && a2tp && a2tp->isa_aryptr()) {
+      a1tap = a1tp->is_aryptr();
+      a2tap = a2tp->is_aryptr();
+      a1tp = a1tap->elem()->make_ptr();
+      a2tp = a2tap->elem()->make_ptr();
+    }
+    if (a1tp && a1tp->isa_instptr() && a2tp && a2tp->isa_instptr()) {
+      if (e1) *e1 = a1tp->is_instptr();
+      if (e2) *e2 = a2tp->is_instptr();
+    }
+  }
+}
+
 //---------------------------get_typeflow_type---------------------------------
 // Import a type produced by ciTypeFlow.
 const Type* Type::get_typeflow_type(ciType* type) {
@@ -1986,7 +2013,11 @@
 bool TypeAry::interface_vs_oop_helper(const Type *t) const {
   const TypeAry* t_ary = t->is_ary();
   if (t_ary) {
-    return _elem->interface_vs_oop(t_ary->_elem);
+    const TypePtr* this_ptr = _elem->make_ptr(); // In case we have narrow_oops
+    const TypePtr*    t_ptr = t_ary->_elem->make_ptr();
+    if(this_ptr != NULL && t_ptr != NULL) {
+      return this_ptr->interface_vs_oop(t_ptr);
+    }
   }
   return Type::interface_vs_oop_helper(t);
 }
@@ -2838,8 +2869,17 @@
     // be 'I' or 'j/l/O'.  Thus we'll pick 'j/l/O'.  If this then flows
     // into a Phi which "knows" it's an Interface type we'll have to
     // uplift the type.
-    if (!empty() && ktip != NULL && ktip->is_loaded() && ktip->klass()->is_interface())
-      return kills;             // Uplift to interface
+    if (!empty()) {
+      if (ktip != NULL && ktip->is_loaded() && ktip->klass()->is_interface()) {
+        return kills;           // Uplift to interface
+      }
+      // Also check for evil cases of 'this' being a class array
+      // and 'kills' expecting an array of interfaces.
+      Type::get_arrays_base_elements(ft, kills, NULL, &ktip);
+      if (ktip != NULL && ktip->is_loaded() && ktip->klass()->is_interface()) {
+        return kills;           // Uplift to array of interface
+      }
+    }
 
     return Type::TOP;           // Canonical empty value
   }
--- a/src/share/vm/opto/type.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/opto/type.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -368,6 +368,11 @@
     return _const_basic_type[type];
   }
 
+  // For two instance arrays of same dimension, return the base element types.
+  // Otherwise or if the arrays have different dimensions, return NULL.
+  static void get_arrays_base_elements(const Type *a1, const Type *a2,
+                                       const TypeInstPtr **e1, const TypeInstPtr **e2);
+
   // Mapping to the array element's basic type.
   BasicType array_element_basic_type() const;
 
--- a/src/share/vm/prims/jvm.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/prims/jvm.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -2628,7 +2628,6 @@
   switch (cp->tag_at(cp_index).value()) {
     case JVM_CONSTANT_InterfaceMethodref:
     case JVM_CONSTANT_Methodref:
-    case JVM_CONSTANT_NameAndType:  // for invokedynamic
       return cp->uncached_name_ref_at(cp_index)->as_utf8();
     default:
       fatal("JVM_GetCPMethodNameUTF: illegal constant");
@@ -2646,7 +2645,6 @@
   switch (cp->tag_at(cp_index).value()) {
     case JVM_CONSTANT_InterfaceMethodref:
     case JVM_CONSTANT_Methodref:
-    case JVM_CONSTANT_NameAndType:  // for invokedynamic
       return cp->uncached_signature_ref_at(cp_index)->as_utf8();
     default:
       fatal("JVM_GetCPMethodSignatureUTF: illegal constant");
@@ -2872,7 +2870,18 @@
 int jio_vsnprintf(char *str, size_t count, const char *fmt, va_list args) {
   // see bug 4399518, 4417214
   if ((intptr_t)count <= 0) return -1;
-  return vsnprintf(str, count, fmt, args);
+
+  int result = vsnprintf(str, count, fmt, args);
+  // Note: on truncation vsnprintf(3) on Unix returns number of
+  // characters which would have been written had the buffer been large
+  // enough; on Windows, it returns -1. We handle both cases here and
+  // always return -1, and perform null termination.
+  if ((result > 0 && (size_t)result >= count) || result == -1) {
+    str[count - 1] = '\0';
+    result = -1;
+  }
+
+  return result;
 }
 
 ATTRIBUTE_PRINTF(3, 0)
--- a/src/share/vm/prims/jvmtiEnter.xsl	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/prims/jvmtiEnter.xsl	Wed Nov 16 12:32:54 2016 -0800
@@ -631,8 +631,8 @@
   jint trace_flags = JvmtiTrace::trace_flags(</xsl:text>
       <xsl:value-of select="@num"/>
       <xsl:text>);
-  const char *func_name;
-  const char *curr_thread_name;
+  const char *func_name = NULL;
+  const char *curr_thread_name = NULL;
   if (trace_flags) {
     func_name = JvmtiTrace::function_name(</xsl:text>
       <xsl:value-of select="@num"/>
--- a/src/share/vm/prims/jvmtiEnv.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/prims/jvmtiEnv.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -957,7 +957,7 @@
     return JVMTI_ERROR_INVALID_THREAD;
 
   Handle thread_obj(current_thread, thread_oop);
-  typeArrayHandle    name;
+  Handle name;
   ThreadPriority priority;
   Handle     thread_group;
   Handle context_class_loader;
@@ -965,7 +965,7 @@
 
   { MutexLocker mu(Threads_lock);
 
-    name = typeArrayHandle(current_thread, java_lang_Thread::name(thread_obj()));
+    name = Handle(current_thread, java_lang_Thread::name(thread_obj()));
     priority = java_lang_Thread::priority(thread_obj());
     thread_group = Handle(current_thread, java_lang_Thread::threadGroup(thread_obj()));
     is_daemon = java_lang_Thread::is_daemon(thread_obj());
@@ -976,7 +976,7 @@
   { const char *n;
 
     if (name() != NULL) {
-      n = UNICODE::as_utf8((jchar*) name->base(T_CHAR), name->length());
+      n = java_lang_String::as_utf8_string(name());
     } else {
       n = UNICODE::as_utf8(NULL, 0);
     }
@@ -3021,7 +3021,7 @@
     // in thread.cpp.
     JvmtiPendingMonitors::enter(rmonitor);
   } else {
-    int r;
+    int r = 0;
     Thread* thread = Thread::current();
 
     if (thread->is_Java_thread()) {
@@ -3084,7 +3084,7 @@
       err = JVMTI_ERROR_NOT_MONITOR_OWNER;
     }
   } else {
-    int r;
+    int r = 0;
     Thread* thread = Thread::current();
 
     if (thread->is_Java_thread()) {
@@ -3118,7 +3118,7 @@
 // rmonitor - pre-checked for validity
 jvmtiError
 JvmtiEnv::RawMonitorWait(JvmtiRawMonitor * rmonitor, jlong millis) {
-  int r;
+  int r = 0;
   Thread* thread = Thread::current();
 
   if (thread->is_Java_thread()) {
@@ -3177,7 +3177,7 @@
 // rmonitor - pre-checked for validity
 jvmtiError
 JvmtiEnv::RawMonitorNotify(JvmtiRawMonitor * rmonitor) {
-  int r;
+  int r = 0;
   Thread* thread = Thread::current();
 
   if (thread->is_Java_thread()) {
@@ -3208,7 +3208,7 @@
 // rmonitor - pre-checked for validity
 jvmtiError
 JvmtiEnv::RawMonitorNotifyAll(JvmtiRawMonitor * rmonitor) {
-  int r;
+  int r = 0;
   Thread* thread = Thread::current();
 
   if (thread->is_Java_thread()) {
--- a/src/share/vm/prims/jvmtiEnvBase.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/prims/jvmtiEnvBase.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -511,7 +511,7 @@
 // mean much better out of memory handling
 unsigned char *
 JvmtiEnvBase::jvmtiMalloc(jlong size) {
-  unsigned char* mem;
+  unsigned char* mem = NULL;
   jvmtiError result = allocate(size, &mem);
   assert(result == JVMTI_ERROR_NONE, "Allocate failed");
   return mem;
@@ -1038,7 +1038,7 @@
     // implied else: entry_count == 0
   }
 
-  int nWant,nWait;
+  int nWant = 0, nWait = 0;
   if (mon != NULL) {
     // this object has a heavyweight monitor
     nWant = mon->contentions(); // # of threads contending for monitor
--- a/src/share/vm/prims/jvmtiExport.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/prims/jvmtiExport.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -995,7 +995,9 @@
         // Before we call the JVMTI agent, we have to set the state in the
         // thread for which we are proxying.
         JavaThreadState prev_state = real_thread->thread_state();
-        assert(prev_state == _thread_blocked, "JavaThread should be at safepoint");
+        assert(((Thread *)real_thread)->is_ConcurrentGC_thread() ||
+               (real_thread->is_Java_thread() && prev_state == _thread_blocked),
+               "should be ConcurrentGCThread or JavaThread at safepoint");
         real_thread->set_thread_state(_thread_in_native);
 
         jvmtiExtensionEvent callback = env->ext_callbacks()->ClassUnload;
--- a/src/share/vm/prims/jvmtiRedefineClasses.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/prims/jvmtiRedefineClasses.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -332,7 +332,7 @@
       int new_name_and_type_ref_i = find_or_append_indirect_entry(scratch_cp, name_and_type_ref_i,
                                                           merge_cp_p, merge_cp_length_p, THREAD);
 
-      const char *entry_name;
+      const char *entry_name = NULL;
       switch (scratch_cp->tag_at(scratch_i).value()) {
       case JVM_CONSTANT_Fieldref:
         entry_name = "Fieldref";
@@ -3926,6 +3926,10 @@
   scratch_class->set_methods(_old_methods);     // To prevent potential GCing of the old methods,
                                           // and to be able to undo operation easily.
 
+  Array<int>* old_ordering = the_class->method_ordering();
+  the_class->set_method_ordering(scratch_class->method_ordering());
+  scratch_class->set_method_ordering(old_ordering);
+
   ConstantPool* old_constants = the_class->constants();
   the_class->set_constants(scratch_class->constants());
   scratch_class->set_constants(old_constants);  // See the previous comment.
--- a/src/share/vm/prims/jvmtiTrace.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/prims/jvmtiTrace.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -266,11 +266,11 @@
   if (threadObj == NULL) {
     return "NULL";
   }
-  typeArrayOop name = java_lang_Thread::name(threadObj);
+  oop name = java_lang_Thread::name(threadObj);
   if (name == NULL) {
     return "<NOT FILLED IN>";
   }
-  return UNICODE::as_utf8((jchar*) name->base(T_CHAR), name->length());
+  return java_lang_String::as_utf8_string(name);
 }
 
 
--- a/src/share/vm/prims/unsafe.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/prims/unsafe.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -864,7 +864,7 @@
 
 UNSAFE_ENTRY(jint, Unsafe_ArrayBaseOffset(JNIEnv *env, jobject unsafe, jclass acls))
   UnsafeWrapper("Unsafe_ArrayBaseOffset");
-  int base, scale;
+  int base = 0, scale = 0;
   getBaseAndScale(base, scale, acls, CHECK_0);
   return field_offset_from_byte_offset(base);
 UNSAFE_END
@@ -872,7 +872,7 @@
 
 UNSAFE_ENTRY(jint, Unsafe_ArrayIndexScale(JNIEnv *env, jobject unsafe, jclass acls))
   UnsafeWrapper("Unsafe_ArrayIndexScale");
-  int base, scale;
+  int base = 0, scale = 0;
   getBaseAndScale(base, scale, acls, CHECK_0);
   // This VM packs both fields and array elements down to the byte.
   // But watch out:  If this changes, so that array references for
--- a/src/share/vm/prims/whitebox.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/prims/whitebox.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -25,6 +25,7 @@
 #include "precompiled.hpp"
 
 #include "memory/metadataFactory.hpp"
+#include "memory/metaspaceShared.hpp"
 #include "memory/universe.hpp"
 #include "oops/oop.inline.hpp"
 
@@ -914,6 +915,10 @@
   return (jlong) MetaspaceGC::capacity_until_GC();
 WB_END
 
+WB_ENTRY(jboolean, WB_IsSharedClass(JNIEnv* env, jobject wb, jclass clazz))
+  return (jboolean)MetaspaceShared::is_in_shared_space(java_lang_Class::as_Klass(JNIHandles::resolve_non_null(clazz)));
+WB_END
+
 WB_ENTRY(jboolean, WB_IsMonitorInflated(JNIEnv* env, jobject wb, jobject obj))
   oop obj_oop = JNIHandles::resolve(obj);
   return (jboolean) obj_oop->mark()->has_monitor();
@@ -1034,6 +1039,7 @@
   {CC"runMemoryUnitTests", CC"()V",                   (void*)&WB_RunMemoryUnitTests},
   {CC"readFromNoaccessArea",CC"()V",                  (void*)&WB_ReadFromNoaccessArea},
   {CC"stressVirtualSpaceResize",CC"(JJJ)I",           (void*)&WB_StressVirtualSpaceResize},
+  {CC"isSharedClass", CC"(Ljava/lang/Class;)Z",       (void*)&WB_IsSharedClass },
 #if INCLUDE_ALL_GCS
   {CC"g1InConcurrentMark", CC"()Z",                   (void*)&WB_G1InConcurrentMark},
   {CC"g1IsHumongous",      CC"(Ljava/lang/Object;)Z", (void*)&WB_G1IsHumongous     },
--- a/src/share/vm/runtime/arguments.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/runtime/arguments.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -560,8 +560,9 @@
       (os::file_name_strcmp(ext, ".jar") == 0 ||
        os::file_name_strcmp(ext, ".zip") == 0);
     if (isJarOrZip) {
-      char* jarpath = NEW_C_HEAP_ARRAY(char, directory_len + 2 + strlen(name), mtInternal);
-      sprintf(jarpath, "%s%s%s", directory, dir_sep, name);
+      size_t length = directory_len + 2 + strlen(name);
+      char* jarpath = NEW_C_HEAP_ARRAY(char, length, mtInternal);
+      jio_snprintf(jarpath, length, "%s%s%s", directory, dir_sep, name);
       path = add_to_path(path, jarpath, false);
       FREE_C_HEAP_ARRAY(char, jarpath, mtInternal);
     }
@@ -704,9 +705,10 @@
   } else if (new_len == 0) {
     value = old_value;
   } else {
-    char* buf = NEW_C_HEAP_ARRAY(char, old_len + 1 + new_len + 1, mtInternal);
+    size_t length = old_len + 1 + new_len + 1;
+    char* buf = NEW_C_HEAP_ARRAY(char, length, mtInternal);
     // each new setting adds another LINE to the switch:
-    sprintf(buf, "%s\n%s", old_value, new_value);
+    jio_snprintf(buf, length, "%s\n%s", old_value, new_value);
     value = buf;
     free_this_too = buf;
   }
@@ -813,15 +815,17 @@
   if (args == NULL || count == 0) {
     return NULL;
   }
-  size_t length = strlen(args[0]) + 1; // add 1 for the null terminator
-  for (int i = 1; i < count; i++) {
-    length += strlen(args[i]) + 1; // add 1 for a space
+  size_t length = 0;
+  for (int i = 0; i < count; i++) {
+    length += strlen(args[i]) + 1; // add 1 for a space or NULL terminating character
   }
   char* s = NEW_RESOURCE_ARRAY(char, length);
-  strcpy(s, args[0]);
-  for (int j = 1; j < count; j++) {
-    strcat(s, " ");
-    strcat(s, args[j]);
+  char* dst = s;
+  for (int j = 0; j < count; j++) {
+    size_t offset = strlen(args[j]) + 1; // add 1 for a space or NULL terminating character
+    jio_snprintf(dst, length, "%s ", args[j]); // jio_snprintf will replace the last space character with NULL character
+    dst += offset;
+    length -= offset;
   }
   return (const char*) s;
 }
@@ -1677,9 +1681,8 @@
   FLAG_SET_DEFAULT(ParallelGCThreads,
                      Abstract_VM_Version::parallel_worker_threads());
   if (ParallelGCThreads == 0) {
-    FLAG_SET_DEFAULT(ParallelGCThreads,
-                     Abstract_VM_Version::parallel_worker_threads());
-  }
+    vm_exit_during_initialization("The flag -XX:+UseG1GC can not be combined with -XX:ParallelGCThreads=0", NULL);
+    }
 
 #if INCLUDE_ALL_GCS
   if (G1ConcRefinementThreads == 0) {
@@ -1892,7 +1895,7 @@
 
     // Feed the cache size setting into the JDK
     char buffer[1024];
-    sprintf(buffer, "java.lang.Integer.IntegerCache.high=" INTX_FORMAT, AutoBoxCacheMax);
+    jio_snprintf(buffer, 1024, "java.lang.Integer.IntegerCache.high=" INTX_FORMAT, AutoBoxCacheMax);
     add_property(buffer);
   }
   if (AggressiveOpts && FLAG_IS_DEFAULT(BiasedLockingStartupDelay)) {
@@ -2769,7 +2772,9 @@
 
         char *options = NULL;
         if(pos != NULL) {
-          options = strcpy(NEW_C_HEAP_ARRAY(char, strlen(pos + 1) + 1, mtInternal), pos + 1);
+          size_t length = strlen(pos + 1) + 1;
+          options = NEW_C_HEAP_ARRAY(char, length, mtInternal);
+          jio_snprintf(options, length, "%s", pos + 1);
         }
 #if !INCLUDE_JVMTI
         if (valid_hprof_or_jdwp_agent(name, is_absolute_path)) {
@@ -2788,7 +2793,9 @@
       return JNI_ERR;
 #else
       if(tail != NULL) {
-        char *options = strcpy(NEW_C_HEAP_ARRAY(char, strlen(tail) + 1, mtInternal), tail);
+        size_t length = strlen(tail) + 1;
+        char *options = NEW_C_HEAP_ARRAY(char, length, mtInternal);
+        jio_snprintf(options, length, "%s", tail);
         add_init_agent("instrument", options, false);
       }
 #endif // !INCLUDE_JVMTI
@@ -3657,8 +3664,7 @@
         }
       } else {
         char buffer[256];
-        strcpy(buffer, "java.awt.headless=");
-        strcat(buffer, envbuffer);
+        jio_snprintf(buffer, 256, "java.awt.headless=%s", envbuffer);
         if (!add_property(buffer)) {
           return JNI_ENOMEM;
         }
@@ -3757,6 +3763,14 @@
 
 void Arguments::set_shared_spaces_flags() {
   if (DumpSharedSpaces) {
+    if (FailOverToOldVerifier) {
+      // Don't fall back to the old verifier on verification failure. If a
+      // class fails verification with the split verifier, it might fail the
+      // CDS runtime verifier constraint check. In that case, we don't want
+      // to share the class. We only archive classes that pass the split verifier.
+      FLAG_SET_DEFAULT(FailOverToOldVerifier, false);
+    }
+
     if (RequireSharedSpaces) {
       warning("cannot dump shared archive while using shared archive");
     }
--- a/src/share/vm/runtime/deoptimization.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/runtime/deoptimization.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -2141,8 +2141,6 @@
                        trap_reason_name(reason),
                        recomp_flag ? " recompiled" : "");
   }
-  if (len >= buflen)
-    buf[buflen-1] = '\0';
   return buf;
 }
 
@@ -2236,8 +2234,6 @@
 #endif
                        );
   }
-  if (len >= buflen)
-    buf[buflen-1] = '\0';
   return buf;
 }
 
--- a/src/share/vm/runtime/globals.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/runtime/globals.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -2283,6 +2283,14 @@
   diagnostic(bool, VerifyDuringGC, false,                                   \
           "Verify memory system during GC (between phases)")                \
                                                                             \
+  diagnostic(ccstrlist, VerifySubSet, "",                                   \
+          "Memory sub-systems to verify when Verify*GC flag(s) "            \
+          "are enabled. One or more sub-systems can be specified "          \
+          "in a comma separated string. Sub-systems are: "                  \
+          "threads, heap, symbol_table, string_table, codecache, "          \
+          "dictionary, classloader_data_graph, metaspace, jni_handles, "    \
+          "c-heap, codecache_oops")                                         \
+                                                                            \
   diagnostic(bool, GCParallelVerificationEnabled, true,                     \
           "Enable parallel memory system verification")                     \
                                                                             \
--- a/src/share/vm/runtime/java.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/runtime/java.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -805,25 +805,36 @@
 }
 
 void JDK_Version::to_string(char* buffer, size_t buflen) const {
+  assert(buffer && buflen > 0, "call with useful buffer");
   size_t index = 0;
   if (!is_valid()) {
     jio_snprintf(buffer, buflen, "%s", "(uninitialized)");
   } else if (is_partially_initialized()) {
     jio_snprintf(buffer, buflen, "%s", "(uninitialized) pre-1.6.0");
   } else {
-    index += jio_snprintf(
+    int rc = jio_snprintf(
         &buffer[index], buflen - index, "%d.%d", _major, _minor);
+    if (rc == -1) return;
+    index += rc;
     if (_micro > 0) {
-      index += jio_snprintf(&buffer[index], buflen - index, ".%d", _micro);
+      rc = jio_snprintf(&buffer[index], buflen - index, ".%d", _micro);
+      if (rc == -1) return;
+      index += rc;
     }
     if (_update > 0) {
-      index += jio_snprintf(&buffer[index], buflen - index, "_%02d", _update);
+      rc = jio_snprintf(&buffer[index], buflen - index, "_%02d", _update);
+      if (rc == -1) return;
+      index += rc;
     }
     if (_special > 0) {
-      index += jio_snprintf(&buffer[index], buflen - index, "%c", _special);
+      rc = jio_snprintf(&buffer[index], buflen - index, "%c", _special);
+      if (rc == -1) return;
+      index += rc;
     }
     if (_build > 0) {
-      index += jio_snprintf(&buffer[index], buflen - index, "-b%02d", _build);
+      rc = jio_snprintf(&buffer[index], buflen - index, "-b%02d", _build);
+      if (rc == -1) return;
+      index += rc;
     }
   }
 }
--- a/src/share/vm/runtime/os.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/runtime/os.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -325,6 +325,10 @@
   // We need to initialize large page support here because ergonomics takes some
   // decisions depending on large page support and the calculated large page size.
   large_page_init();
+
+  // VM version initialization identifies some characteristics of the
+  // the platform that are used during ergonomic decisions.
+  VM_Version::init_before_ergo();
 }
 
 void os::signal_init() {
--- a/src/share/vm/runtime/safepoint.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/runtime/safepoint.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -142,7 +142,7 @@
 
   // Save the starting time, so that it can be compared to see if this has taken
   // too long to complete.
-  jlong safepoint_limit_time;
+  jlong safepoint_limit_time = 0;
   timeout_error_printed = false;
 
   // PrintSafepointStatisticsTimeout can be specified separately. When
@@ -925,7 +925,7 @@
 
 
 void ThreadSafepointState::print_on(outputStream *st) const {
-  const char *s;
+  const char *s = NULL;
 
   switch(_type) {
     case _running                : s = "_running";              break;
--- a/src/share/vm/runtime/sharedRuntime.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/runtime/sharedRuntime.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -2909,8 +2909,6 @@
   char *s = sig->as_C_string();
   int len = (int)strlen(s);
   s++; len--;                   // Skip opening paren
-  char *t = s+len;
-  while( *(--t) != ')' ) ;      // Find close paren
 
   BasicType *sig_bt = NEW_RESOURCE_ARRAY( BasicType, 256 );
   VMRegPair *regs = NEW_RESOURCE_ARRAY( VMRegPair, 256 );
@@ -2919,7 +2917,7 @@
     sig_bt[cnt++] = T_OBJECT; // Receiver is argument 0; not in signature
   }
 
-  while( s < t ) {
+  while( *s != ')' ) {          // Find closing right paren
     switch( *s++ ) {            // Switch on signature character
     case 'B': sig_bt[cnt++] = T_BYTE;    break;
     case 'C': sig_bt[cnt++] = T_CHAR;    break;
--- a/src/share/vm/runtime/sharedRuntime.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/runtime/sharedRuntime.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -145,6 +145,12 @@
   static double dsqrt(double f);
 #endif
 
+  // Montgomery multiplication
+  static void montgomery_multiply(jint *a_ints, jint *b_ints, jint *n_ints,
+                                  jint len, jlong inv, jint *m_ints);
+  static void montgomery_square(jint *a_ints, jint *n_ints,
+                                jint len, jlong inv, jint *m_ints);
+
 #ifdef __SOFTFP__
   // C++ compiler generates soft float instructions as well as passing
   // float and double in registers.
--- a/src/share/vm/runtime/signature.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/runtime/signature.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -225,7 +225,49 @@
   _index = 0;
   expect('(');
   Symbol* sig = _signature;
-  while (sig->byte_at(_index) != ')') _index++;
+  // Need to skip over each type in the signature's argument list until a
+  // closing ')' is found., then get the return type.  We cannot just scan
+  // for the first ')' because ')' is a legal character in a type name.
+  while (sig->byte_at(_index) != ')') {
+    switch(sig->byte_at(_index)) {
+      case 'B':
+      case 'C':
+      case 'D':
+      case 'F':
+      case 'I':
+      case 'J':
+      case 'S':
+      case 'Z':
+      case 'V':
+        {
+          _index++;
+        }
+        break;
+      case 'L':
+        {
+          while (sig->byte_at(_index++) != ';') ;
+        }
+        break;
+      case '[':
+        {
+          int begin = ++_index;
+          skip_optional_size();
+          while (sig->byte_at(_index) == '[') {
+            _index++;
+            skip_optional_size();
+          }
+          if (sig->byte_at(_index) == 'L') {
+            while (sig->byte_at(_index++) != ';') ;
+          } else {
+            _index++;
+          }
+        }
+        break;
+      default:
+        ShouldNotReachHere();
+        break;
+    }
+  }
   expect(')');
   // Parse return type
   _parameter_index = -1;
--- a/src/share/vm/runtime/stubRoutines.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/runtime/stubRoutines.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -136,6 +136,10 @@
 address StubRoutines::_crc_table_adr = NULL;
 
 address StubRoutines::_multiplyToLen = NULL;
+address StubRoutines::_squareToLen = NULL;
+address StubRoutines::_mulAdd = NULL;
+address StubRoutines::_montgomeryMultiply = NULL;
+address StubRoutines::_montgomerySquare = NULL;
 
 double (* StubRoutines::_intrinsic_log   )(double) = NULL;
 double (* StubRoutines::_intrinsic_log10 )(double) = NULL;
--- a/src/share/vm/runtime/stubRoutines.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/runtime/stubRoutines.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -209,6 +209,10 @@
   static address _crc_table_adr;
 
   static address _multiplyToLen;
+  static address _squareToLen;
+  static address _mulAdd;
+  static address _montgomeryMultiply;
+  static address _montgomerySquare;
 
   // These are versions of the java.lang.Math methods which perform
   // the same operations as the intrinsic version.  They are used for
@@ -367,6 +371,10 @@
   static address crc_table_addr()      { return _crc_table_adr; }
 
   static address multiplyToLen()       {return _multiplyToLen; }
+  static address squareToLen()         {return _squareToLen; }
+  static address mulAdd()              {return _mulAdd; }
+  static address montgomeryMultiply()  { return _montgomeryMultiply; }
+  static address montgomerySquare()    { return _montgomerySquare; }
 
   static address select_fill_function(BasicType t, bool aligned, const char* &name);
 
--- a/src/share/vm/runtime/thread.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/runtime/thread.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -2987,13 +2987,13 @@
   const char* name_str;
   oop thread_obj = threadObj();
   if (thread_obj != NULL) {
-    typeArrayOop name = java_lang_Thread::name(thread_obj);
+    oop name = java_lang_Thread::name(thread_obj);
     if (name != NULL) {
       if (buf == NULL) {
-        name_str = UNICODE::as_utf8((jchar*) name->base(T_CHAR), name->length());
+        name_str = java_lang_String::as_utf8_string(name);
       }
       else {
-        name_str = UNICODE::as_utf8((jchar*) name->base(T_CHAR), name->length(), buf, buflen);
+        name_str = java_lang_String::as_utf8_string(name, buf, buflen);
       }
     }
     else if (is_attaching_via_jni()) { // workaround for 6412693 - see 6404306
--- a/src/share/vm/runtime/vmStructs.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/runtime/vmStructs.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -823,6 +823,8 @@
      static_field(StubRoutines,                _updateBytesCRC32,                             address)                               \
      static_field(StubRoutines,                _crc_table_adr,                                address)                               \
      static_field(StubRoutines,                _multiplyToLen,                                address)                               \
+     static_field(StubRoutines,                _squareToLen,                                  address)                               \
+     static_field(StubRoutines,                _mulAdd,                                       address)                               \
      static_field(StubRoutines,                _jbyte_arraycopy,                              address)                               \
      static_field(StubRoutines,                _jshort_arraycopy,                             address)                               \
      static_field(StubRoutines,                _jint_arraycopy,                               address)                               \
--- a/src/share/vm/runtime/vm_version.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/runtime/vm_version.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -54,6 +54,12 @@
                                                   unsigned int dem,
                                                   unsigned int switch_pt);
  public:
+  // Called as part of the runtime services initialization which is
+  // called from the management module initialization (via init_globals())
+  // after argument parsing and attaching of the main thread has
+  // occurred.  Examines a variety of the hardware capabilities of
+  // the platform to determine which features can be used to execute the
+  // program.
   static void initialize();
 
   // This allows for early initialization of VM_Version information
@@ -63,6 +69,11 @@
   // need to specialize this define VM_Version::early_initialize().
   static void early_initialize() { }
 
+  // Called to initialize VM variables needing initialization
+  // after command line parsing. Platforms that need to specialize
+  // this should define VM_Version::init_before_ergo().
+  static void init_before_ergo() {}
+
   // Name
   static const char* vm_name();
   // Vendor
--- a/src/share/vm/services/diagnosticCommand.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/services/diagnosticCommand.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -437,6 +437,10 @@
   ("config.file",
    "set com.sun.management.config.file", "STRING", false),
 
+  _jmxremote_host
+  ("jmxremote.host",
+   "set com.sun.management.jmxremote.host", "STRING", false),
+
   _jmxremote_port
   ("jmxremote.port",
    "set com.sun.management.jmxremote.port", "STRING", false),
@@ -516,6 +520,7 @@
 
   {
     _dcmdparser.add_dcmd_option(&_config_file);
+    _dcmdparser.add_dcmd_option(&_jmxremote_host);
     _dcmdparser.add_dcmd_option(&_jmxremote_port);
     _dcmdparser.add_dcmd_option(&_jmxremote_rmi_port);
     _dcmdparser.add_dcmd_option(&_jmxremote_ssl);
@@ -586,6 +591,7 @@
     }
 
     PUT_OPTION(_config_file);
+    PUT_OPTION(_jmxremote_host);
     PUT_OPTION(_jmxremote_port);
     PUT_OPTION(_jmxremote_rmi_port);
     PUT_OPTION(_jmxremote_ssl);
--- a/src/share/vm/services/diagnosticCommand.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/services/diagnosticCommand.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -280,6 +280,7 @@
   // com.sun.management is omitted
 
   DCmdArgument<char *> _config_file;
+  DCmdArgument<char *> _jmxremote_host;
   DCmdArgument<char *> _jmxremote_port;
   DCmdArgument<char *> _jmxremote_rmi_port;
   DCmdArgument<char *> _jmxremote_ssl;
--- a/src/share/vm/services/heapDumper.cpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/services/heapDumper.cpp	Wed Nov 16 12:32:54 2016 -0800
@@ -376,11 +376,11 @@
   };
 
   int _fd;              // file descriptor (-1 if dump file not open)
-  jlong _bytes_written; // number of byte written to dump file
+  julong _bytes_written; // number of byte written to dump file
 
   char* _buffer;    // internal buffer
-  int _size;
-  int _pos;
+  size_t _size;
+  size_t _pos;
 
   char* _error;   // error message when I/O fails
 
@@ -388,14 +388,14 @@
   int file_descriptor() const                   { return _fd; }
 
   char* buffer() const                          { return _buffer; }
-  int buffer_size() const                       { return _size; }
-  int position() const                          { return _pos; }
-  void set_position(int pos)                    { _pos = pos; }
+  size_t buffer_size() const                    { return _size; }
+  size_t position() const                       { return _pos; }
+  void set_position(size_t pos)                 { _pos = pos; }
 
   void set_error(const char* error)             { _error = (char*)os::strdup(error); }
 
   // all I/O go through this function
-  void write_internal(void* s, int len);
+  void write_internal(void* s, size_t len);
 
  public:
   DumpWriter(const char* path);
@@ -406,14 +406,14 @@
   void flush();
 
   // total number of bytes written to the disk
-  jlong bytes_written() const           { return _bytes_written; }
+  julong bytes_written() const          { return _bytes_written; }
 
   // adjust the number of bytes written to disk (used to keep the count
   // of the number of bytes written in case of rewrites)
-  void adjust_bytes_written(jlong n)     { _bytes_written += n; }
+  void adjust_bytes_written(jlong n)    { _bytes_written += n; }
 
   // number of (buffered) bytes as yet unwritten to the dump file
-  jlong bytes_unwritten() const          { return (jlong)position(); }
+  size_t bytes_unwritten() const        { return position(); }
 
   char* error() const                   { return _error; }
 
@@ -421,7 +421,7 @@
   void seek_to_offset(jlong pos);
 
   // writer functions
-  void write_raw(void* s, int len);
+  void write_raw(void* s, size_t len);
   void write_u1(u1 x)                   { write_raw((void*)&x, 1); }
   void write_u2(u2 x);
   void write_u4(u4 x);
@@ -474,29 +474,33 @@
 }
 
 // write directly to the file
-void DumpWriter::write_internal(void* s, int len) {
+void DumpWriter::write_internal(void* s, size_t len) {
   if (is_open()) {
-    int n = ::write(file_descriptor(), s, len);
-    if (n > 0) {
-      _bytes_written += n;
-    }
-    if (n != len) {
+    const char* pos = (char*)s;
+    ssize_t n = 0;
+    while (len > 0) {
+      uint tmp = (uint)MIN2(len, (size_t)UINT_MAX);
+      n = ::write(file_descriptor(), pos, tmp);
+
       if (n < 0) {
         set_error(strerror(errno));
-      } else {
-        set_error("file size limit");
+        ::close(file_descriptor());
+        set_file_descriptor(-1);
+        return;
       }
-      ::close(file_descriptor());
-      set_file_descriptor(-1);
+
+      _bytes_written += n;
+      pos += n;
+      len -= n;
     }
   }
 }
 
 // write raw bytes
-void DumpWriter::write_raw(void* s, int len) {
+void DumpWriter::write_raw(void* s, size_t len) {
   if (is_open()) {
-    // flush buffer to make toom
-    if ((position()+ len) >= buffer_size()) {
+    // flush buffer to make room
+    if ((position() + len) >= buffer_size()) {
       flush();
     }
 
@@ -519,13 +523,12 @@
   }
 }
 
-
 jlong DumpWriter::current_offset() {
   if (is_open()) {
     // the offset is the file offset plus whatever we have buffered
     jlong offset = os::current_file_offset(file_descriptor());
     assert(offset >= 0, "lseek failed");
-    return offset + (jlong)position();
+    return offset + position();
   } else {
     return (jlong)-1;
   }
@@ -774,7 +777,7 @@
   HandleMark hm;
   instanceKlassHandle ikh = instanceKlassHandle(Thread::current(), k);
 
-  int size = 0;
+  u4 size = 0;
 
   for (FieldStream fld(ikh, false, false); !fld.eos(); fld.next()) {
     if (!fld.access_flags().is_static()) {
@@ -799,7 +802,7 @@
       }
     }
   }
-  return (u4)size;
+  return size;
 }
 
 // dumps static fields of the given class
@@ -1031,8 +1034,7 @@
   }
 
   // If the byte ordering is big endian then we can copy most types directly
-  int length_in_bytes = array->length() * type2aelembytes(type);
-  assert(length_in_bytes > 0, "nothing to copy");
+  u4 length_in_bytes = (u4)array->length() * type2aelembytes(type);
 
   switch (type) {
     case T_INT : {
@@ -1285,22 +1287,18 @@
     }
   }
 
-  // create a HPROF_GC_INSTANCE record for each object
   if (o->is_instance()) {
+    // create a HPROF_GC_INSTANCE record for each object
     DumperSupport::dump_instance(writer(), o);
     mark_end_of_record();
-  } else {
+  } else if (o->is_objArray()) {
     // create a HPROF_GC_OBJ_ARRAY_DUMP record for each object array
-    if (o->is_objArray()) {
-      DumperSupport::dump_object_array(writer(), objArrayOop(o));
-      mark_end_of_record();
-    } else {
-      // create a HPROF_GC_PRIM_ARRAY_DUMP record for each type array
-      if (o->is_typeArray()) {
-        DumperSupport::dump_prim_array(writer(), typeArrayOop(o));
-        mark_end_of_record();
-      }
-    }
+    DumperSupport::dump_object_array(writer(), objArrayOop(o));
+    mark_end_of_record();
+  } else if (o->is_typeArray()) {
+    // create a HPROF_GC_PRIM_ARRAY_DUMP record for each type array
+    DumperSupport::dump_prim_array(writer(), typeArrayOop(o));
+    mark_end_of_record();
   }
 }
 
@@ -1448,11 +1446,11 @@
     assert(dump_start() >= 0, "no dump start recorded");
 
     // calculate the size of the dump record
-    jlong dump_end = writer()->current_offset();
-    jlong dump_len = (dump_end - dump_start() - 4);
+    julong dump_end = writer()->current_offset();
+    julong dump_len = (dump_end - dump_start() - 4);
 
     // record length must fit in a u4
-    if (dump_len > (jlong)(4L*(jlong)G)) {
+    if (dump_len > max_juint) {
       warning("record is too large");
     }
 
@@ -1461,7 +1459,7 @@
     writer()->write_u4((u4)dump_len);
 
     // adjust the total size written to keep the bytes written correct.
-    writer()->adjust_bytes_written(-((long) sizeof(u4)));
+    writer()->adjust_bytes_written(-((jlong) sizeof(u4)));
 
     // seek to dump end so we can continue
     writer()->seek_to_offset(dump_end);
@@ -1477,12 +1475,12 @@
   if (writer()->is_open()) {
     if (is_segmented_dump()) {
       // don't use current_offset that would be too expensive on a per record basis
-      jlong dump_end = writer()->bytes_written() + writer()->bytes_unwritten();
-      assert(dump_end == writer()->current_offset(), "checking");
-      jlong dump_len = (dump_end - dump_start() - 4);
-      assert(dump_len >= 0 && dump_len <= max_juint, "bad dump length");
+      julong dump_end = writer()->bytes_written() + writer()->bytes_unwritten();
+      assert(dump_end == (julong)writer()->current_offset(), "checking");
+      julong dump_len = (dump_end - dump_start() - 4);
+      assert(dump_len <= max_juint, "bad dump length");
 
-      if (dump_len > (jlong)HeapDumpSegmentSize) {
+      if (dump_len > HeapDumpSegmentSize) {
         write_current_dump_record_length();
         write_dump_header();
       }
@@ -1868,13 +1866,8 @@
   if (print_to_tty()) {
     timer()->stop();
     if (error() == NULL) {
-      char msg[256];
-      sprintf(msg, "Heap dump file created [%s bytes in %3.3f secs]",
-        JLONG_FORMAT, timer()->seconds());
-PRAGMA_DIAG_PUSH
-PRAGMA_FORMAT_NONLITERAL_IGNORED_INTERNAL
-      tty->print_cr(msg, writer.bytes_written());
-PRAGMA_DIAG_POP
+      tty->print_cr("Heap dump file created [" JULONG_FORMAT " bytes in %3.3f secs]",
+                    writer.bytes_written(), timer()->seconds());
     } else {
       tty->print_cr("Dump file is incomplete: %s", writer.error());
     }
--- a/src/share/vm/services/threadService.hpp	Wed Nov 09 14:41:57 2016 -0800
+++ b/src/share/vm/services/threadService.hpp	Wed Nov 16 12:32:54 2016 -0800
@@ -425,12 +425,12 @@
   }
 
   JavaThreadStatusChanger(JavaThread* java_thread,
-                          java_lang_Thread::ThreadStatus state) {
+                          java_lang_Thread::ThreadStatus state) : _old_state(java_lang_Thread::NEW) {
     save_old_state(java_thread);
     set_thread_status(state);
   }
 
-  JavaThreadStatusChanger(JavaThread* java_thread) {
+  JavaThreadStatusChanger(JavaThread* java_thread) : _old_state(java_lang_Thread::NEW) {
     save_old_state(java_thread);
   }
 
@@ -527,7 +527,7 @@
   // Current thread is the notifying thread which holds the monitor.
   static bool wait_reenter_begin(JavaThread *java_thread, ObjectMonitor *obj_m) {
     assert((java_thread != NULL), "Java thread should not be null here");
-    bool active  = false;
+    bool active = false;
     if (is_alive(java_thread) && ServiceUtil::visible_oop((oop)obj_m->object())) {
       active = contended_enter_begin(java_thread);
     }
@@ -542,7 +542,7 @@
   }
 
   JavaThreadBlockedOnMonitorEnterState(JavaThread *java_thread, ObjectMonitor *obj_m) :
-    JavaThreadStatusChanger(java_thread) {
+    _stat(NULL), _active(false), JavaThreadStatusChanger(java_thread) {
     assert((java_thread != NULL), "Java thread should not be null here");
     // Change thread status and collect contended enter stats for monitor contended
     // enter done for external java world objects and it is contended. All other cases
--- a/test/TEST.groups	Wed Nov 09 14:41:57 2016 -0800
+++ b/test/TEST.groups	Wed Nov 16 12:32:54 2016 -0800
@@ -61,7 +61,6 @@
 # can be resolved in some cases by using tools from the compile-jdk.
 #
 needs_jdk = \
-  gc/TestG1ZeroPGCTJcmdThreadPrint.java \
   gc/metaspace/CompressedClassSpaceSizeInJmapHeap.java \
   gc/metaspace/TestMetaspacePerfCounters.java \
   gc/metaspace/TestPerfCountersAndMemoryPools.java \
@@ -216,6 +215,7 @@
   runtime/NMT \
   gc/class_unloading/TestCMSClassUnloadingEnabledHWM.java \
   gc/class_unloading/TestG1ClassUnloadingHWM.java \
+  gc/ergonomics/TestDynamicNumberOfGCThreads.java \
   gc/g1/TestRegionAlignment.java \
   gc/g1/TestShrinkToOneRegion.java \
   gc/metaspace/G1AddMetaspaceDependency.java \
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/compiler/c1/TestArrayCopyToFromObject.java	Wed Nov 16 12:32:54 2016 -0800
@@ -0,0 +1,64 @@
+/*
+ * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/*
+ * @test
+ * @bug 8160591
+ * @summary C1-generated code for System.arraycopy() does not throw an ArrayStoreException if 'dst' is no a "proper" array (i.e., it is java.lang.Object)
+ * @run main/othervm -XX:+IgnoreUnrecognizedVMOptions -XX:+TieredCompilation -XX:TieredStopAtLevel=1 -Xcomp -XX:-UseCompressedClassPointers -XX:CompileOnly=TestArrayCopyToFromObject.test TestArrayCopyToFromObject
+ * @run main/othervm -XX:+IgnoreUnrecognizedVMOptions -XX:+TieredCompilation -XX:TieredStopAtLevel=1 -Xcomp -XX:+UseCompressedClassPointers -XX:CompileOnly=TestArrayCopyToFromObject.test TestArrayCopyToFromObject
+ */
+public class TestArrayCopyToFromObject {
+
+    public void test(Object aArray[]) {
+        Object a = new Object();
+
+        try {
+            System.arraycopy(aArray, 0, a, 0, 1);
+            throw new RuntimeException ("FAILED: Expected ArrayStoreException " +
+                                        "(due to destination not being an array) " +
+                                        "was not thrown");
+        } catch (ArrayStoreException e) {
+            System.out.println("PASSED: Expected ArrayStoreException was thrown");
+        }
+
+        try {
+            System.arraycopy(a, 0, aArray, 0, 1);
+            throw new RuntimeException ("FAILED: Expected ArrayStoreException " +
+                                        "(due to source not being an array) " +
+                                        "was not thrown");
+        } catch (ArrayStoreException e) {
+            System.out.println("PASSED: Expected ArrayStoreException was thrown");
+        }
+
+    }
+
+    public static void main(String args[]) {
+        System.out.println("TestArrayCopyToFromObject");
+        Object aArray[] = new Object[10];
+        for (int i = 0; i < 10; i++) {
+            aArray[i] = new Object();
+        }
+        new TestArrayCopyToFromObject().test(aArray);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/compiler/floatingpoint/TestPow2.java	Wed Nov 16 12:32:54 2016 -0800
@@ -0,0 +1,73 @@
+/*
+ * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/*
+ * @test
+ * @bug 8063086
+ * @summary X^2 special case for C2 yields different result than interpreter
+ * @library /testlibrary /testlibrary/whitebox /compiler/whitebox
+ * @build TestPow2
+ * @run main ClassFileInstaller sun.hotspot.WhiteBox
+ * @run main/othervm -Xbootclasspath/a:. -XX:+UnlockDiagnosticVMOptions -XX:+WhiteBoxAPI
+ *                   -XX:-BackgroundCompilation -XX:-UseOnStackReplacement TestPow2
+ *
+ */
+
+import java.lang.reflect.*;
+import sun.hotspot.WhiteBox;
+
+public class TestPow2 {
+
+    private static final WhiteBox WHITE_BOX = WhiteBox.getWhiteBox();
+
+    private static final double base = 5350.456329377186;
+    private static final double exp = 2.0;
+
+    static double m() {
+        return Math.pow(base, exp);
+    }
+
+    static public void main(String[] args) throws NoSuchMethodException {
+        Method test_method = TestPow2.class.getDeclaredMethod("m");
+
+        double interpreter_result = m();
+
+        // Compile with C1 if possible
+        WHITE_BOX.enqueueMethodForCompilation(test_method, CompilerWhiteBoxTest.COMP_LEVEL_SIMPLE);
+
+        double c1_result = m();
+
+        WHITE_BOX.deoptimizeMethod(test_method);
+
+        // Compile it with C2 if possible
+        WHITE_BOX.enqueueMethodForCompilation(test_method, CompilerWhiteBoxTest.COMP_LEVEL_FULL_OPTIMIZATION);
+
+        double c2_result = m();
+
+        if (interpreter_result != c1_result || interpreter_result != c2_result ||
+            c1_result != c2_result) {
+            System.out.println("interpreter = " + interpreter_result + " c1 = " + c1_result + " c2 = " + c2_result);
+            throw new RuntimeException("Test Failed");
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/compiler/intrinsics/montgomerymultiply/MontgomeryMultiplyTest.java	Wed Nov 16 12:32:54 2016 -0800
@@ -0,0 +1,284 @@
+//
+// Copyright (c) 2000, 2015, Oracle and/or its affiliates. All rights reserved.
+// Copyright (c) 2015, Red Hat Inc. All rights reserved.
+// DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+//
+// This code is free software; you can redistribute it and/or modify it
+// under the terms of the GNU General Public License version 2 only, as
+// published by the Free Software Foundation.
+//
+// This code is distributed in the hope that it will be useful, but WITHOUT
+// ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+// version 2 for more details (a copy is included in the LICENSE file that
+// accompanied this code).
+//
+// You should have received a copy of the GNU General Public License version
+// 2 along with this work; if not, write to the Free Software Foundation,
+// Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+//
+// Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+// or visit www.oracle.com if you need additional information or have any
+// questions.
+//
+//
+
+import java.lang.invoke.MethodHandle;
+import java.lang.invoke.MethodHandles;
+import java.lang.invoke.MethodType;
+import java.lang.reflect.Constructor;
+import java.lang.reflect.Field;
+import java.lang.reflect.Method;
+import java.math.BigInteger;
+import java.util.Arrays;
+import java.util.Random;
+
+/**
+ * @test
+ * @bug 8130150
+ * @library /testlibrary
+ * @requires (os.simpleArch == "x64") & (os.family != "windows")
+ * @summary Verify that the Montgomery multiply intrinsic works and correctly checks its arguments.
+ * @run main/othervm -XX:+IgnoreUnrecognizedVMOptions -XX:+UseMontgomerySquareIntrinsic
+ *      -XX:+UseMontgomeryMultiplyIntrinsic MontgomeryMultiplyTest
+ * @run main/othervm -XX:+IgnoreUnrecognizedVMOptions -XX:+UseMontgomerySquareIntrinsic
+ *      -XX:-UseMontgomeryMultiplyIntrinsic MontgomeryMultiplyTest
+ * @run main/othervm -XX:+IgnoreUnrecognizedVMOptions -XX:-UseMontgomerySquareIntrinsic
+ *      -XX:+UseMontgomeryMultiplyIntrinsic MontgomeryMultiplyTest
+ */
+
+public class MontgomeryMultiplyTest {
+
+    static final MethodHandles.Lookup lookup = MethodHandles.lookup();
+
+    static final MethodHandle montgomeryMultiplyHandle, montgomerySquareHandle;
+    static final MethodHandle bigIntegerConstructorHandle;
+    static final Field bigIntegerMagField;
+
+    static {
+       // Use reflection to gain access to the methods we want to test.
+        try {
+            Method m = BigInteger.class.getDeclaredMethod("montgomeryMultiply",
+                /*a*/int[].class, /*b*/int[].class, /*n*/int[].class, /*len*/int.class,
+                /*inv*/long.class, /*product*/int[].class);
+            m.setAccessible(true);
+            montgomeryMultiplyHandle = lookup.unreflect(m);
+
+            m = BigInteger.class.getDeclaredMethod("montgomerySquare",
+                /*a*/int[].class, /*n*/int[].class, /*len*/int.class,
+                /*inv*/long.class, /*product*/int[].class);
+            m.setAccessible(true);
+            montgomerySquareHandle = lookup.unreflect(m);
+
+            Constructor c
+                = BigInteger.class.getDeclaredConstructor(int.class, int[].class);
+            c.setAccessible(true);
+            bigIntegerConstructorHandle = lookup.unreflectConstructor(c);
+
+            bigIntegerMagField = BigInteger.class.getDeclaredField("mag");
+            bigIntegerMagField.setAccessible(true);
+
+        } catch (Throwable ex) {
+            throw new RuntimeException(ex);
+        }
+    }
+
+    // Invoke either BigInteger.montgomeryMultiply or BigInteger.montgomerySquare.
+    int[] montgomeryMultiply(int[] a, int[] b, int[] n, int len, long inv,
+                             int[] product) throws Throwable {
+        int[] result =
+            (a == b) ? (int[]) montgomerySquareHandle.invokeExact(a, n, len, inv, product)
+                     : (int[]) montgomeryMultiplyHandle.invokeExact(a, b, n, len, inv, product);
+        return Arrays.copyOf(result, len);
+    }
+
+    // Invoke the private constructor BigInteger(int[]).
+    BigInteger newBigInteger(int[] val) throws Throwable {
+        return (BigInteger) bigIntegerConstructorHandle.invokeExact(1, val);
+    }
+
+    // Get the private field BigInteger.mag
+    int[] mag(BigInteger n) {
+        try {
+            return (int[]) bigIntegerMagField.get(n);
+        } catch (Exception ex) {
+            throw new RuntimeException(ex);
+        }
+    }
+
+    // Montgomery multiplication
+    // Calculate a * b * r^-1 mod n)
+    //
+    // R is a power of the word size
+    // N' = R^-1 mod N
+    //
+    // T := ab
+    // m := (T mod R)N' mod R [so 0 <= m < R]
+    // t := (T + mN)/R
+    // if t >= N then return t - N else return t
+    //
+    BigInteger montgomeryMultiply(BigInteger a, BigInteger b, BigInteger N,
+            int len, BigInteger n_prime)
+            throws Throwable {
+        BigInteger T = a.multiply(b);
+        BigInteger R = BigInteger.ONE.shiftLeft(len*32);
+        BigInteger mask = R.subtract(BigInteger.ONE);
+        BigInteger m = (T.and(mask)).multiply(n_prime);
+        m = m.and(mask); // i.e. m.mod(R)
+        T = T.add(m.multiply(N));
+        T = T.shiftRight(len*32); // i.e. T.divide(R)
+        if (T.compareTo(N) > 0) {
+            T = T.subtract(N);
+        }
+        return T;
+    }
+
+    // Call the Montgomery multiply intrinsic.
+    BigInteger montgomeryMultiply(int[] a_words, int[] b_words, int[] n_words,
+            int len, BigInteger inv)
+            throws Throwable {
+        BigInteger t = montgomeryMultiply(
+                newBigInteger(a_words),
+                newBigInteger(b_words),
+                newBigInteger(n_words),
+                len, inv);
+        return t;
+    }
+
+    // Check that the Montgomery multiply intrinsic returns the same
+    // result as the longhand calculation.
+    void check(int[] a_words, int[] b_words, int[] n_words, int len, BigInteger inv)
+            throws Throwable {
+        BigInteger n = newBigInteger(n_words);
+        BigInteger slow = montgomeryMultiply(a_words, b_words, n_words, len, inv);
+        BigInteger fast
+            = newBigInteger(montgomeryMultiply
+                            (a_words, b_words, n_words, len, inv.longValue(), null));
+        // The intrinsic may not return the same value as the longhand
+        // calculation but they must have the same residue mod N.
+        if (!slow.mod(n).equals(fast.mod(n))) {
+            throw new RuntimeException();
+        }
+    }
+
+    Random rnd = new Random(0);
+
+    // Return a random value of length <= bits in an array of even length
+    int[] random_val(int bits) {
+        int len = (bits+63)/64;  // i.e. length in longs
+        int[] val = new int[len*2];
+        for (int i = 0; i < val.length; i++)
+            val[i] = rnd.nextInt();
+        int leadingZeros = 64 - (bits & 64);
+        if (leadingZeros >= 32) {
+            val[0] = 0;
+            val[1] &= ~(-1l << (leadingZeros & 31));
+        } else {
+            val[0] &= ~(-1l << leadingZeros);
+        }
+        return val;
+    }
+
+    void testOneLength(int lenInBits, int lenInInts) throws Throwable {
+        BigInteger mod = new BigInteger(lenInBits, 2, rnd);
+        BigInteger r = BigInteger.ONE.shiftLeft(lenInInts * 32);
+        BigInteger n_prime = mod.modInverse(r).negate();
+
+        // Make n.length even, padding with a zero if necessary
+        int[] n = mag(mod);
+        if (n.length < lenInInts) {
+            int[] x = new int[lenInInts];
+            System.arraycopy(n, 0, x, lenInInts-n.length, n.length);
+            n = x;
+        }
+
+        for (int i = 0; i < 10000; i++) {
+            // multiply
+            check(random_val(lenInBits), random_val(lenInBits), n, lenInInts, n_prime);
+            // square
+            int[] tmp = random_val(lenInBits);
+            check(tmp, tmp, n, lenInInts, n_prime);
+        }
+    }
+
+    // Test the Montgomery multiply intrinsic with a bunch of random
+    // values of varying lengths.  Do this for long enough that the
+    // caller of the intrinsic is C2-compiled.
+    void testResultValues() throws Throwable {
+        // Test a couple of interesting edge cases.
+        testOneLength(1024, 32);
+        testOneLength(1025, 34);
+        for (int j = 10; j > 0; j--) {
+            // Construct a random prime whose length in words is even
+            int lenInBits = rnd.nextInt(2048) + 64;
+            int lenInInts = (lenInBits + 63)/64*2;
+            testOneLength(lenInBits, lenInInts);
+        }
+    }
+
+    // Range checks
+    void testOneMontgomeryMultiplyCheck(int[] a, int[] b, int[] n, int len, long inv,
+                                        int[] product, Class klass) {
+        try {
+            montgomeryMultiply(a, b, n, len, inv, product);
+        } catch (Throwable ex) {
+            if (klass.isAssignableFrom(ex.getClass()))
+                return;
+            throw new RuntimeException(klass + " expected, " + ex + " was thrown");
+        }
+        throw new RuntimeException(klass + " expected, was not thrown");
+    }
+
+    void testOneMontgomeryMultiplyCheck(int[] a, int[] b, BigInteger n, int len, BigInteger inv,
+            Class klass) {
+        testOneMontgomeryMultiplyCheck(a, b, mag(n), len, inv.longValue(), null, klass);
+    }
+
+    void testOneMontgomeryMultiplyCheck(int[] a, int[] b, BigInteger n, int len, BigInteger inv,
+            int[] product, Class klass) {
+        testOneMontgomeryMultiplyCheck(a, b, mag(n), len, inv.longValue(), product, klass);
+    }
+
+    void testMontgomeryMultiplyChecks() {
+        int[] blah = random_val(40);
+        int[] small = random_val(39);
+        BigInteger mod = new BigInteger(40*32 , 2, rnd);
+        BigInteger r = BigInteger.ONE.shiftLeft(40*32);
+        BigInteger n_prime = mod.modInverse(r).negate();
+
+        // Length out of range: square
+        testOneMontgomeryMultiplyCheck(blah, blah, mod, 41, n_prime, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(blah, blah, mod, 0, n_prime, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(blah, blah, mod, -1, n_prime, IllegalArgumentException.class);
+        // As above, but for multiply
+        testOneMontgomeryMultiplyCheck(blah, blah.clone(), mod, 41, n_prime, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(blah, blah.clone(), mod, 0, n_prime, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(blah, blah.clone(), mod, 0, n_prime, IllegalArgumentException.class);
+
+        // Length odd
+        testOneMontgomeryMultiplyCheck(small, small, mod, 39, n_prime, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(small, small, mod, 0, n_prime, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(small, small, mod, -1, n_prime, IllegalArgumentException.class);
+        // As above, but for multiply
+        testOneMontgomeryMultiplyCheck(small, small.clone(), mod, 39, n_prime, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(small, small.clone(), mod, 0, n_prime, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(small, small.clone(), mod, -1, n_prime, IllegalArgumentException.class);
+
+        // array too small
+        testOneMontgomeryMultiplyCheck(blah, blah, mod, 40, n_prime, small, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(blah, blah.clone(), mod, 40, n_prime, small, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(small, blah, mod, 40, n_prime, blah, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(blah, small, mod, 40, n_prime, blah, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(blah, blah, mod, 40, n_prime, small, IllegalArgumentException.class);
+        testOneMontgomeryMultiplyCheck(small, small, mod, 40, n_prime, blah, IllegalArgumentException.class);
+    }
+
+    public static void main(String args[]) {
+        try {
+            new MontgomeryMultiplyTest().testMontgomeryMultiplyChecks();
+            new MontgomeryMultiplyTest().testResultValues();
+        } catch (Throwable ex) {
+            throw new RuntimeException(ex);
+        }
+     }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/compiler/intrinsics/muladd/TestMulAdd.java	Wed Nov 16 12:32:54 2016 -0800
@@ -0,0 +1,118 @@
+/*
+ * 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 8081778
+ * @summary Add C2 x86 intrinsic for BigInteger::mulAdd() method
+ *
+ * @run main/othervm/timeout=600 -XX:-TieredCompilation -Xbatch
+ *      -XX:+IgnoreUnrecognizedVMOptions -XX:-UseSquareToLenIntrinsic -XX:-UseMultiplyToLenIntrinsic
+ *      -XX:+UseMulAddIntrinsic
+ *      -XX:CompileCommand=dontinline,TestMulAdd::main
+ *      -XX:CompileCommand=option,TestMulAdd::base_multiply,ccstr,DisableIntrinsic,_mulAdd
+ *      -XX:CompileCommand=option,java.math.BigInteger::multiply,ccstr,DisableIntrinsic,_mulAdd
+ *      -XX:CompileCommand=option,java.math.BigInteger::square,ccstr,DisableIntrinsic,_mulAdd
+ *      -XX:CompileCommand=option,java.math.BigInteger::squareToLen,ccstr,DisableIntrinsic,_mulAdd
+ *      -XX:CompileCommand=option,java.math.BigInteger::mulAdd,ccstr,DisableIntrinsic,_mulAdd
+ *      -XX:CompileCommand=inline,java.math.BigInteger::multiply
+ *      -XX:CompileCommand=inline,java.math.BigInteger::square
+ *      -XX:CompileCommand=inline,java.math.BigInteger::squareToLen
+ *      -XX:CompileCommand=inline,java.math.BigInteger::mulAdd TestMulAdd
+ */
+
+import java.util.Random;
+import java.math.*;
+
+public class TestMulAdd {
+
+    // Avoid intrinsic by preventing inlining multiply() and mulAdd().
+    public static BigInteger base_multiply(BigInteger op1) {
+      return op1.multiply(op1);
+    }
+
+    // Generate mulAdd() intrinsic by inlining multiply().
+    public static BigInteger new_multiply(BigInteger op1) {
+      return op1.multiply(op1);
+    }
+
+    public static boolean bytecompare(BigInteger b1, BigInteger b2) {
+      byte[] data1 = b1.toByteArray();
+      byte[] data2 = b2.toByteArray();
+      if (data1.length != data2.length)
+        return false;
+      for (int i = 0; i < data1.length; i++) {
+        if (data1[i] != data2[i])
+          return false;
+      }
+      return true;
+    }
+
+    public static String stringify(BigInteger b) {
+      String strout= "";
+      byte [] data = b.toByteArray();
+      for (int i = 0; i < data.length; i++) {
+        strout += (String.format("%02x",data[i]) + " ");
+      }
+      return strout;
+    }
+
+    public static void main(String args[]) throws Exception {
+
+      BigInteger oldsum = new BigInteger("0");
+      BigInteger newsum = new BigInteger("0");
+
+      BigInteger b1, b2, oldres, newres;
+
+      Random rand = new Random();
+      long seed = System.nanoTime();
+      Random rand1 = new Random();
+      long seed1 = System.nanoTime();
+      rand.setSeed(seed);
+      rand1.setSeed(seed1);
+
+      for (int j = 0; j < 100000; j++) {
+        int rand_int = rand1.nextInt(3136)+32;
+        b1 = new BigInteger(rand_int, rand);
+
+        oldres = base_multiply(b1);
+        newres = new_multiply(b1);
+
+        oldsum = oldsum.add(oldres);
+        newsum = newsum.add(newres);
+
+        if (!bytecompare(oldres,newres)) {
+          System.out.print("mismatch for:b1:" + stringify(b1) + " :oldres:" + stringify(oldres) + " :newres:" + stringify(newres));
+          System.out.println(b1);
+          throw new Exception("Failed");
+        }
+      }
+      if (!bytecompare(oldsum,newsum))  {
+        System.out.println("Failure: oldsum:" + stringify(oldsum) + " newsum:" + stringify(newsum));
+        throw new Exception("Failed");
+      } else {
+        System.out.println("Success");
+      }
+   }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/compiler/intrinsics/squaretolen/TestSquareToLen.java	Wed Nov 16 12:32:54 2016 -0800
@@ -0,0 +1,116 @@
+/*
+ * 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 8081778
+ * @summary Add C2 x86 intrinsic for BigInteger::squareToLen() method
+ *
+ * @run main/othervm/timeout=600 -XX:-TieredCompilation -Xbatch
+ *      -XX:+IgnoreUnrecognizedVMOptions
+ *      -XX:+UseSquareToLenIntrinsic
+ *      -XX:CompileCommand=exclude,TestSquareToLen::main
+ *      -XX:CompileCommand=option,TestSquareToLen::base_multiply,ccstr,DisableIntrinsic,_squareToLen
+ *      -XX:CompileCommand=option,java.math.BigInteger::multiply,ccstr,DisableIntrinsic,_squareToLen
+ *      -XX:CompileCommand=option,java.math.BigInteger::square,ccstr,DisableIntrinsic,_squareToLen
+ *      -XX:CompileCommand=option,java.math.BigInteger::squareToLen,ccstr,DisableIntrinsic,_squareToLen
+ *      -XX:CompileCommand=inline,java.math.BigInteger::multiply
+ *      -XX:CompileCommand=inline,java.math.BigInteger::square
+ *      -XX:CompileCommand=inline,java.math.BigInteger::squareToLen TestSquareToLen
+ */
+
+import java.util.Random;
+import java.math.*;
+
+public class TestSquareToLen {
+
+    // Avoid intrinsic by preventing inlining multiply() and squareToLen().
+    public static BigInteger base_multiply(BigInteger op1) {
+      return op1.multiply(op1);
+    }
+
+    // Generate squareToLen() intrinsic by inlining multiply().
+    public static BigInteger new_multiply(BigInteger op1) {
+      return op1.multiply(op1);
+    }
+
+    public static boolean bytecompare(BigInteger b1, BigInteger b2) {
+      byte[] data1 = b1.toByteArray();
+      byte[] data2 = b2.toByteArray();
+      if (data1.length != data2.length)
+        return false;
+      for (int i = 0; i < data1.length; i++) {
+        if (data1[i] != data2[i])
+          return false;
+      }
+      return true;
+    }
+
+    public static String stringify(BigInteger b) {
+      String strout= "";
+      byte [] data = b.toByteArray();
+      for (int i = 0; i < data.length; i++) {
+        strout += (String.format("%02x",data[i]) + " ");
+      }
+      return strout;
+    }
+
+    public static void main(String args[]) throws Exception {
+
+      BigInteger oldsum = new BigInteger("0");
+      BigInteger newsum = new BigInteger("0");
+
+      BigInteger b1, b2, oldres, newres;
+
+      Random rand = new Random();
+      long seed = System.nanoTime();
+      Random rand1 = new Random();
+      long seed1 = System.nanoTime();
+      rand.setSeed(seed);
+      rand1.setSeed(seed1);
+
+      for (int j = 0; j < 100000; j++) {
+        int rand_int = rand1.nextInt(3136)+32;
+        b1 = new BigInteger(rand_int, rand);
+
+        oldres = base_multiply(b1);
+        newres = new_multiply(b1);
+
+        oldsum = oldsum.add(oldres);
+        newsum = newsum.add(newres);
+
+        if (!bytecompare(oldres,newres)) {
+          System.out.print("mismatch for:b1:" + stringify(b1) + " :oldres:" + stringify(oldres) + " :newres:" + stringify(newres));
+          System.out.println(b1);
+          throw new Exception("Failed");
+        }
+      }
+      if (!bytecompare(oldsum,newsum))  {
+        System.out.println("Failure: oldsum:" + stringify(oldsum) + " newsum:" + stringify(newsum));
+        throw new Exception("Failed");
+      } else {
+        System.out.println("Success");
+      }
+   }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/compiler/jsr292/LongReferenceCastingTest.java	Wed Nov 16 12:32:54 2016 -0800
@@ -0,0 +1,75 @@
+/*
+ * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+
+import java.lang.invoke.*;
+
+/**
+ * @test
+ * @bug 8148752
+ * @summary Test correct casting of MH arguments during inlining.
+ * @run main LongReferenceCastingTest
+ */
+public class LongReferenceCastingTest {
+    static final String MY_STRING = "myString";
+    static final MethodHandle MH;
+
+    static {
+        try {
+            MethodHandles.Lookup lookup = MethodHandles.lookup();
+            MethodType mt = MethodType.methodType(String.class, long.class, Object.class, String.class);
+            MH = lookup.findVirtual(LongReferenceCastingTest.class, "myMethod", mt);
+        } catch (Exception e) {
+            throw new Error(e);
+        }
+    }
+
+    public String myMethod(long l, Object o, String s) {
+        // The long argument occupies two stack slots, causing C2 to treat it as
+        // two arguments and casting the fist one two long and the second one to Object.
+        // As a result, Object o is casted to String and the o.toString() call is
+        // inlined as String::toString(). We fail at runtime because 'o' is not a String.
+        return o.toString();
+    }
+
+    public String toString() {
+        return MY_STRING;
+    }
+
+    public static void main(String[] args) throws Exception {
+        LongReferenceCastingTest test = new LongReferenceCastingTest();
+        try {
+            for (int i = 0; i < 20_000; ++i) {
+                if (!test.invoke().equals(MY_STRING)) {
+                    throw new RuntimeException("Invalid string");
+                }
+            }
+        } catch (Throwable t) {
+            throw new RuntimeException("Test failed", t);
+        }
+    }
+
+    public String invoke() throws Throwable {
+        return (String) MH.invokeExact(this, 0L, (Object)this, MY_STRING);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/compiler/loopopts/TestArraysFillDeadControl.java	Wed Nov 16 12:32:54 2016 -0800
@@ -0,0 +1,53 @@
+/*
+ * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ *
+ */
+
+/**
+ * @test
+ * @bug 8147645
+ * @summary Array.fill intrinsification code doesn't mark replaced control as dead
+ * @run main/othervm  -XX:-TieredCompilation -XX:CompileCommand=dontinline,TestArraysFillDeadControl::dont_inline TestArraysFillDeadControl
+ *
+ */
+
+import java.util.Arrays;
+
+public class TestArraysFillDeadControl {
+
+    static void dont_inline() {
+    }
+
+    static int i = 1;
+
+    public static void main(String[] args) {
+        for (int j = 0; j < 200000; j++) {
+            int[] a = new int[2];
+            int b = i;
+
+            Arrays.fill(a, 1);
+            Arrays.fill(a, 1+b);
+
+            dont_inline();
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/compiler/loopopts/TestLoopPeeling.java	Wed Nov 16 12:32:54 2016 -0800
@@ -0,0 +1,100 @@
+/*
+ * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/*
+ * @test
+ * @bug 8078262
+ * @summary Tests correct dominator information after loop peeling.
+ * @run main/othervm -Xcomp -XX:CompileCommand=compileonly,TestLoopPeeling::test* TestLoopPeeling
+ */
+public class TestLoopPeeling {
+
+    public int[] array = new int[100];
+
+    public static void main(String args[]) {
+        TestLoopPeeling test = new TestLoopPeeling();
+        try {
+            test.testArrayAccess(0, 1);
+            test.testArrayAllocation(0, 1);
+        } catch (Exception e) {
+            // Ignore exceptions
+        }
+    }
+
+    public void testArrayAccess(int index, int inc) {
+        int storeIndex = -1;
+
+        for (; index < 10; index += inc) {
+            // This loop invariant check triggers loop peeling because it can
+            // be moved out of the loop (see 'IdealLoopTree::policy_peeling').
+            if (inc == 42) return;
+
+            // This loop variant usage of LShiftL( ConvI2L( Phi(storeIndex) ) )
+            // prevents the split if optimization that would otherwise clone the
+            // LShiftL and ConvI2L nodes and assign them to their corresponding array
+            // address computation (see 'PhaseIdealLoop::split_if_with_blocks_post').
+            if (storeIndex > 0 && array[storeIndex] == 42) return;
+
+            if (index == 42) {
+                // This store and the corresponding range check are moved out of the
+                // loop and both used after old loop and the peeled iteration exit.
+                // For the peeled iteration, storeIndex is always -1 and the ConvI2L
+                // is replaced by TOP. However, the range check is not folded because
+                // we don't do the split if optimization in PhaseIdealLoop2.
+                // As a result, we have a (dead) control path from the peeled iteration
+                // to the StoreI but the data path is removed.
+                array[storeIndex] = 1;
+                return;
+            }
+
+            storeIndex++;
+        }
+    }
+
+    public byte[] testArrayAllocation(int index, int inc) {
+        int allocationCount = -1;
+        byte[] result;
+
+        for (; index < 10; index += inc) {
+            // This loop invariant check triggers loop peeling because it can
+            // be moved out of the loop (see 'IdealLoopTree::policy_peeling').
+            if (inc == 42) return null;
+
+            if (index == 42) {
+                // This allocation and the corresponding size check are moved out of the
+                // loop and both used after old loop and the peeled iteration exit.
+                // For the peeled iteration, allocationCount is always -1 and the ConvI2L
+                // is replaced by TOP. However, the size check is not folded because
+                // we don't do the split if optimization in PhaseIdealLoop2.
+                // As a result, we have a (dead) control path from the peeled iteration
+                // to the allocation but the data path is removed.
+                result = new byte[allocationCount];
+                return result;
+            }
+
+            allocationCount++;
+        }
+        return null;
+    }
+}
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/compiler/stringopts/TestStringObjectInitialization.java	Wed Nov 16 12:32:54 2016 -0800
@@ -0,0 +1,77 @@
+/*
+ * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+
+import java.util.Arrays;
+
+/*
+ * @test
+ * @bug 8159244
+ * @summary Verifies that no partially initialized String object escapes from
+ *          C2's String concat optimization in a highly concurrent setting.
+ *          This test triggers the bug in about 1 out of 10 runs.
+ * @compile -XDstringConcat=inline TestStringObjectInitialization.java
+ * @run main/othervm/timeout=300 -XX:+IgnoreUnrecognizedVMOptions -XX:-UseCompressedOops -XX:-CompactStrings
+ *                               -XX:-UseG1GC -XX:+UseParallelGC TestStringObjectInitialization
+ */
+public class TestStringObjectInitialization {
+
+    String myString;
+
+    public static void main(String[] args) throws Exception {
+        TestStringObjectInitialization t = new TestStringObjectInitialization();
+        // Create some threads that concurrently update 'myString'
+        for (int i = 0; i < 100; ++i) {
+            (new Thread(new Runner(t))).start();
+        }
+        Thread last = new Thread(new Runner(t));
+        last.start();
+        last.join();
+    }
+
+    private void add(String message) {
+        // String escapes to other threads here
+        myString += message;
+    }
+
+    public void run(String s, String[] sArray) {
+        // Trigger C2's string concatenation optimization
+        add(s + Arrays.toString(sArray) + " const ");
+    }
+}
+
+class Runner implements Runnable {
+    private TestStringObjectInitialization test;
+
+    public Runner(TestStringObjectInitialization t) {
+        test = t;
+    }
+
+    public void run(){
+        String[] array = {"a", "b", "c"};
+        for (int i = 0; i < 10000; ++i) {
+            test.run("a", array);
+        }
+    }
+}
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/compiler/types/TestMeetIncompatibleInterfaceArrays.java	Wed Nov 16 12:32:54 2016 -0800
@@ -0,0 +1,351 @@
+/*
+ * Copyright 2015 SAP AG.  All Rights Reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please 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 8141551
+ * @summary C2 can not handle returns with inccompatible interface arrays
+ * @library /testlibrary /testlibrary/whitebox/
+ * @build sun.hotspot.WhiteBox
+ * @run main ClassFileInstaller sun.hotspot.WhiteBox
+ *                              sun.hotspot.WhiteBox$WhiteBoxPermission
+ * @run main/othervm
+ *        -Xbootclasspath/a:.
+ *        -XX:+UnlockDiagnosticVMOptions
+ *        -XX:+WhiteBoxAPI
+ *        -Xbatch
+ *        -XX:CompileThreshold=1
+ *        -XX:-TieredCompilation
+ *        -XX:CICompilerCount=1
+ *        -XX:+PrintCompilation
+ *        -XX:+PrintInlining
+ *        -XX:CompileCommand=compileonly,MeetIncompatibleInterfaceArrays*.run
+ *        -XX:CompileCommand=dontinline,TestMeetIncompatibleInterfaceArrays$Helper.createI2*
+ *        -XX:CompileCommand=quiet
+ *        TestMeetIncompatibleInterfaceArrays 0
+ * @run main/othervm
+ *        -Xbootclasspath/a:.
+ *        -XX:+UnlockDiagnosticVMOptions
+ *        -XX:+WhiteBoxAPI
+ *        -Xbatch
+ *        -XX:CompileThreshold=1
+ *        -XX:-TieredCompilation
+ *        -XX:CICompilerCount=1
+ *        -XX:+PrintCompilation
+ *        -XX:+PrintInlining
+ *        -XX:CompileCommand=compileonly,MeetIncompatibleInterfaceArrays*.run
+ *        -XX:CompileCommand=inline,TestMeetIncompatibleInterfaceArrays$Helper.createI2*
+ *        -XX:CompileCommand=quiet
+ *        TestMeetIncompatibleInterfaceArrays 1
+ * @run main/othervm
+ *        -Xbootclasspath/a:.
+ *        -XX:+UnlockDiagnosticVMOptions
+ *        -XX:+WhiteBoxAPI
+ *        -Xbatch
+ *        -XX:CompileThreshold=1
+ *        -XX:Tier0InvokeNotifyFreqLog=0 -XX:Tier2InvokeNotifyFreqLog=0 -XX:Tier3InvokeNotifyFreqLog=0 -XX:Tier23InlineeNotifyFreqLog=0
+ *        -XX:Tier3InvocationThreshold=2 -XX:Tier3MinInvocationThreshold=2 -XX:Tier3CompileThreshold=2
+ *        -XX:Tier4InvocationThreshold=1 -XX:Tier4MinInvocationThreshold=1 -XX:Tier4CompileThreshold=1
+ *        -XX:+TieredCompilation
+ *        -XX:CICompilerCount=2
+ *        -XX:+PrintCompilation
+ *        -XX:+PrintInlining
+ *        -XX:CompileCommand=compileonly,MeetIncompatibleInterfaceArrays*.run
+ *        -XX:CompileCommand=compileonly,TestMeetIncompatibleInterfaceArrays$Helper.createI2*
+ *        -XX:CompileCommand=inline,TestMeetIncompatibleInterfaceArrays$Helper.createI2*
+ *        -XX:CompileCommand=quiet
+ *        TestMeetIncompatibleInterfaceArrays 2
+ *
+ * @author volker.simonis@gmail.com
+ */
+
+import java.io.FileOutputStream;
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+import jdk.internal.org.objectweb.asm.ClassWriter;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import static jdk.internal.org.objectweb.asm.Opcodes.*;
+import sun.hotspot.WhiteBox;
+
+public class TestMeetIncompatibleInterfaceArrays extends ClassLoader {
+
+    private static final WhiteBox WB = WhiteBox.getWhiteBox();
+
+    public static interface I1 { public String getName(); }
+    public static interface I2 { public String getName(); }
+    public static class I2C implements I2 { public String getName() { return "I2";} }
+    public static class I21C implements I2, I1 { public String getName() { return "I2 and I1";} }
+
+    public static class Helper {
+        public static I2 createI2Array0() {
+            return new I2C();
+        }
+        public static I2[] createI2Array1() {
+            return new I2C[] { new I2C() };
+        }
+        public static I2[][] createI2Array2() {
+            return new I2C[][] { new I2C[] { new I2C() } };
+        }
+        public static I2[][][] createI2Array3() {
+            return new I2C[][][] { new I2C[][] { new I2C[] { new I2C() } } };
+        }
+        public static I2[][][][] createI2Array4() {
+            return new I2C[][][][] { new I2C[][][] { new I2C[][] { new I2C[] { new I2C() } } } };
+        }
+        public static I2[][][][][] createI2Array5() {
+            return new I2C[][][][][] { new I2C[][][][] { new I2C[][][] { new I2C[][] { new I2C[] { new I2C() } } } } };
+        }
+        public static I2 createI21Array0() {
+            return new I21C();
+        }
+        public static I2[] createI21Array1() {
+            return new I21C[] { new I21C() };
+        }
+        public static I2[][] createI21Array2() {
+            return new I21C[][] { new I21C[] { new I21C() } };
+        }
+        public static I2[][][] createI21Array3() {
+            return new I21C[][][] { new I21C[][] { new I21C[] { new I21C() } } };
+        }
+        public static I2[][][][] createI21Array4() {
+            return new I21C[][][][] { new I21C[][][] { new I21C[][] { new I21C[] { new I21C() } } } };
+        }
+        public static I2[][][][][] createI21Array5() {
+            return new I21C[][][][][] { new I21C[][][][] { new I21C[][][] { new I21C[][] { new I21C[] { new I21C() } } } } };
+        }
+    }
+
+    // Location for the generated class files
+    public static final String PATH = System.getProperty("test.classes", ".") + java.io.File.separator;
+
+    /*
+     * With 'good == false' this helper method creates the following classes
+     * (using the nested 'Helper' class and the nested interfaces 'I1' and 'I2').
+     * For brevity I omit the enclosing class 'TestMeetIncompatibleInterfaceArrays' in the
+     * following examples:
+     *
+     * public class MeetIncompatibleInterfaceArrays0ASM {
+     *   public static I1 run() {
+     *     return Helper.createI2Array0(); // returns I2
+     *   }
+     *   public static void test() {
+     *     I1 i1 = run();
+     *     System.out.println(i1.getName());
+     *   }
+     * }
+     * public class MeetIncompatibleInterfaceArrays1ASM {
+     *   public static I1[] run() {
+     *     return Helper.createI2Array1(); // returns I2[]
+     *   }
+     *   public static void test() {
+     *     I1[] i1 = run();
+     *     System.out.println(i1[0].getName());
+     *   }
+     * }
+     * ...
+     * // MeetIncompatibleInterfaceArrays4ASM is special because it creates
+     * // an illegal class which will be rejected by the verifier.
+     * public class MeetIncompatibleInterfaceArrays4ASM {
+     *   public static I1[][][][] run() {
+     *     return Helper.createI2Array3(); // returns I1[][][] which gives a verifier error because return expects I1[][][][]
+     *   }
+     *   public static void test() {
+     *     I1[][][][][] i1 = run();
+     *     System.out.println(i1[0][0][0][0][0].getName());
+     *   }
+     * ...
+     * public class MeetIncompatibleInterfaceArrays5ASM {
+     *   public static I1[][][][][] run() {
+     *     return Helper.createI2Array5(); // returns I2[][][][][]
+     *   }
+     *   public static void test() {
+     *     I1[][][][][] i1 = run();
+     *     System.out.println(i1[0][0][0][0][0].getName());
+     *   }
+     * }
+     *
+     * Notice that this is not legal Java code. We would have to use a cast in "run()" to make it legal:
+     *
+     *   public static I1[] run() {
+     *     return (I1[])Helper.createI2Array1(); // returns I2[]
+     *   }
+     *
+     * But in pure bytecode, the "run()" methods are perfectly legal:
+     *
+     *   public static I1[] run();
+     *     Code:
+     *       0: invokestatic  #16  // Method Helper.createI2Array1:()[LI2;
+     *       3: areturn
+     *
+     * The "test()" method calls the "getName()" function from I1 on the objects returned by "run()".
+     * This will epectedly fail with an "IncompatibleClassChangeError" because the objects returned
+     * by "run()" (and by createI2Array()) are actually of type "I2C" and only implement "I2" but not "I1".
+     *
+     *
+     * With 'good == true' this helper method will create the following classes:
+     *
+     * public class MeetIncompatibleInterfaceArraysGood0ASM {
+     *   public static I1 run() {
+     *     return Helper.createI21Array0(); // returns I2
+     *   }
+     *   public static void test() {
+     *     I1 i1 = run();
+     *     System.out.println(i1.getName());
+     *   }
+     * }
+     *
+     * Calling "test()" on these objects will succeed and output "I2 and I1" because now the "run()"
+     * method calls "createI21Array()" which actually return an object (or an array of objects) of
+     * type "I21C" which implements both "I2" and "I1".
+     *
+     * Notice that at the bytecode level, the code for the "run()" and "test()" methods in
+     * "MeetIncompatibleInterfaceArraysASM" and "MeetIncompatibleInterfaceArraysGoodASM" look exactly
+     * the same. I.e. the verifier has no chance to verify if the I2 object returned by "createI1Array()"
+     * or "createI21Array()" implements "I1" or not. That's actually the reason why both versions of
+     * generated classes are legal from a verifier point of view.
+     *
+     */
+    static void generateTestClass(int dim, boolean good) throws Exception {
+        String baseClassName = "MeetIncompatibleInterfaceArrays";
+        if (good)
+            baseClassName += "Good";
+        String createName = "createI2" + (good ? "1" : "") + "Array";
+        String a = "";
+        for (int i = 0; i < dim; i++)
+            a += "[";
+        ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_FRAMES);
+        cw.visit(V1_8, ACC_PUBLIC, baseClassName + dim + "ASM", null, "java/lang/Object", null);
+        MethodVisitor constr = cw.visitMethod(ACC_PUBLIC, "<init>", "()V", null, null);
+        constr.visitCode();
+        constr.visitVarInsn(ALOAD, 0);
+        constr.visitMethodInsn(INVOKESPECIAL, "java/lang/Object", "<init>", "()V", false);
+        constr.visitInsn(RETURN);
+        constr.visitMaxs(0, 0);
+        constr.visitEnd();
+        MethodVisitor run = cw.visitMethod(ACC_PUBLIC | ACC_STATIC, "run",
+                "()" + a + "LTestMeetIncompatibleInterfaceArrays$I1;", null, null);
+        run.visitCode();
+        if (dim == 4) {
+            run.visitMethodInsn(INVOKESTATIC, "TestMeetIncompatibleInterfaceArrays$Helper", createName + 3,
+                    "()" + "[[[" + "LTestMeetIncompatibleInterfaceArrays$I2;", false);
+        } else {
+            run.visitMethodInsn(INVOKESTATIC, "TestMeetIncompatibleInterfaceArrays$Helper", createName + dim,
+                    "()" + a + "LTestMeetIncompatibleInterfaceArrays$I2;", false);
+        }
+        run.visitInsn(ARETURN);
+        run.visitMaxs(0, 0);
+        run.visitEnd();
+        MethodVisitor test = cw.visitMethod(ACC_PUBLIC | ACC_STATIC, "test", "()V", null, null);
+        test.visitCode();
+        test.visitMethodInsn(INVOKESTATIC, baseClassName + dim + "ASM", "run",
+                "()" + a + "LTestMeetIncompatibleInterfaceArrays$I1;", false);
+        test.visitVarInsn(ASTORE, 0);
+        if (dim > 0) {
+            test.visitVarInsn(ALOAD, 0);
+            for (int i = 1; i <= dim; i++) {
+                test.visitInsn(ICONST_0);
+                test.visitInsn(AALOAD);
+            }
+            test.visitVarInsn(ASTORE, 1);
+        }
+        test.visitFieldInsn(GETSTATIC, "java/lang/System", "out", "Ljava/io/PrintStream;");
+        test.visitVarInsn(ALOAD, dim > 0 ? 1 : 0);
+        test.visitMethodInsn(INVOKEINTERFACE, "TestMeetIncompatibleInterfaceArrays$I1", "getName",
+                "()Ljava/lang/String;", true);
+        test.visitMethodInsn(INVOKEVIRTUAL, "java/io/PrintStream", "println", "(Ljava/lang/Object;)V", false);
+        test.visitInsn(RETURN);
+        test.visitMaxs(0, 0);
+        test.visitEnd();
+
+        // Get the bytes of the class..
+        byte[] b = cw.toByteArray();
+        // ..and write them into a class file (for debugging)
+        FileOutputStream fos = new FileOutputStream(PATH + baseClassName + dim + "ASM.class");
+        fos.write(b);
+        fos.close();
+
+    }
+
+    public static String[][] tier = { { "interpreted", "C2 (tier 4) without inlining", "C2 (tier4) without inlining" },
+            { "interpreted", "C2 (tier 4) with inlining", "C2 (tier4) with inlining" },
+            { "interpreted", "C1 (tier 3) with inlining", "C2 (tier4) with inlining" } };
+
+    public static void main(String[] args) throws Exception {
+        final int pass = Integer.parseInt(args.length > 0 ? args[0] : "0");
+
+        // Load and initialize some classes required for compilation
+        Class.forName("TestMeetIncompatibleInterfaceArrays$I1");
+        Class.forName("TestMeetIncompatibleInterfaceArrays$I2");
+        Class.forName("TestMeetIncompatibleInterfaceArrays$Helper");
+
+        for (int g = 0; g < 2; g++) {
+            String baseClassName = "MeetIncompatibleInterfaceArrays";
+            boolean good = (g == 0) ? false : true;
+            if (good)
+                baseClassName += "Good";
+            for (int i = 0; i < 6; i++) {
+                System.out.println();
+                System.out.println("Creating " + baseClassName + i + "ASM.class");
+                System.out.println("========================================" + "=" + "=========");
+                // Create the "MeetIncompatibleInterfaceArrays<i>ASM" class
+                generateTestClass(i, good);
+                Class<?> c = null;
+                try {
+                    c = Class.forName(baseClassName + i + "ASM");
+                } catch (VerifyError ve) {
+                    if (i == 4) {
+                        System.out.println("OK - must be (" + ve.getMessage() + ").");
+                    } else {
+                        throw ve;
+                    }
+                    continue;
+                }
+                // Call MeetIncompatibleInterfaceArrays<i>ASM.test()
+                Method m = c.getMethod("test");
+                Method r = c.getMethod("run");
+                for (int j = 0; j < 3; j++) {
+                    System.out.println((j + 1) + ". invokation of " + baseClassName + i + "ASM.test() [should be "
+                            + tier[pass][j] + "]");
+                    try {
+                        m.invoke(null);
+                    } catch (InvocationTargetException ite) {
+                        if (good) {
+                            throw ite;
+                        } else {
+                            if (ite.getCause() instanceof IncompatibleClassChangeError) {
+                                System.out.println("  OK - catched InvocationTargetException("
+                                        + ite.getCause().getMessage() + ").");
+                            } else {
+                                throw ite;
+                            }
+                        }
+                    }
+                }
+                System.out.println("Method " + r + (WB.isMethodCompiled(r) ? " has" : " has not") + " been compiled.");
+                if (!WB.isMethodCompiled(r)) {
+                    throw new Exception("Method " + r + " must be compiled!");
+                }
+            }
+        }
+    }
+}
--- a/test/gc/8000311/Test8000311.java	Wed Nov 09 14:41:57 2016 -0800
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,42 +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.
- */
-
-/**
- * @test Test8000311
- * @key gc
- * @bug 8000311
- * @summary G1: ParallelGCThreads==0 broken
- * @run main/othervm -XX:+UseG1GC -XX:ParallelGCThreads=0 -XX:+ResizePLAB -XX:+ExplicitGCInvokesConcurrent Test8000311
- * @author filipp.zhinkin@oracle.com
- */
-
-import java.util.*;
-
-public class Test8000311 {
-  public static void main(String args[]) {
-    for(int i = 0; i<100; i++) {
-      byte[] garbage = new byte[1000];
-      System.gc();
-    }
-  }
-}
--- a/test/gc/TestG1ZeroPGCTJcmdThreadPrint.java	Wed Nov 09 14:41:57 2016 -0800
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,54 +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.
- */
-
-/* @test TestG1ZeroPGCTJcmdThreadPrint
- * @key gc
- * @bug 8005875
- * @summary Use jcmd to generate a thread dump of a Java program being run with PGCT=0 to verify 8005875
- * @library /testlibrary
- * @run main/othervm -XX:+UseG1GC -XX:ParallelGCThreads=0 -XX:+IgnoreUnrecognizedVMOptions TestG1ZeroPGCTJcmdThreadPrint
- */
-
-import com.oracle.java.testlibrary.*;
-
-public class TestG1ZeroPGCTJcmdThreadPrint {
-  public static void main(String args[]) throws Exception {
-
-    // Grab the pid from the current java process
-    String pid = Integer.toString(ProcessTools.getProcessId());
-
-    // Create a ProcessBuilder
-    ProcessBuilder pb = new ProcessBuilder();
-
-    // Run jcmd <pid> Thread.print
-    pb.command(JDKToolFinder.getJDKTool("jcmd"), pid, "Thread.print");
-
-    OutputAnalyzer output = new OutputAnalyzer(pb.start());
-
-    // There shouldn't be a work gang for concurrent marking.
-    output.shouldNotContain("G1 Parallel Marking Threads");
-
-    // Make sure we didn't crash
-    output.shouldHaveExitValue(0);
-  }
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/gc/TestVerifySubSet.java	Wed Nov 16 12:32:54 2016 -0800
@@ -0,0 +1,91 @@
+/*
+ * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/* @test TestVerifySubSet.java
+ * @key gc
+ * @bug 8072725
+ * @summary Test VerifySubSet option
+ * @library /testlibrary
+ */
+
+import com.oracle.java.testlibrary.OutputAnalyzer;
+import com.oracle.java.testlibrary.ProcessTools;
+import java.util.ArrayList;
+import java.util.Collections;
+
+class RunSystemGC {
+    public static void main(String args[]) throws Exception {
+        System.gc();
+    }
+}
+
+public class TestVerifySubSet {
+    private static String[] getTestJavaOpts() {
+        String testVmOptsStr = System.getProperty("test.java.opts");
+        if (!testVmOptsStr.isEmpty()) {
+            return testVmOptsStr.split(" ");
+        } else {
+            return new String[] {};
+        }
+    }
+
+    private static OutputAnalyzer runTest(String subset) throws Exception {
+        ArrayList<String> vmOpts = new ArrayList();
+
+        Collections.addAll(vmOpts, getTestJavaOpts());
+        Collections.addAll(vmOpts, new String[] {"-XX:+UnlockDiagnosticVMOptions",
+                                                 "-XX:+VerifyBeforeGC",
+                                                 "-XX:+VerifyAfterGC",
+                                                 "-XX:VerifySubSet="+subset,
+                                                 RunSystemGC.class.getName()});
+        ProcessBuilder pb =
+            ProcessTools.createJavaProcessBuilder(vmOpts.toArray(new String[vmOpts.size()]));
+        OutputAnalyzer output = new OutputAnalyzer(pb.start());
+
+        System.out.println("Output:\n" + output.getOutput());
+        return output;
+    }
+
+    public static void main(String args[]) throws Exception {
+
+        OutputAnalyzer output;
+
+        output = runTest("heap, threads, codecache, metaspace");
+        output.shouldContain("Heap");
+        output.shouldContain("Threads");
+        output.shouldContain("CodeCache");
+        output.shouldContain("MetaspaceAux");
+        output.shouldNotContain("SymbolTable");
+        output.shouldNotContain("StringTable");
+        output.shouldNotContain("SystemDictionary");
+        output.shouldNotContain("CodeCache Oops");
+        output.shouldHaveExitValue(0);
+
+        output = runTest("hello, threads, codecache, metaspace");
+        output.shouldContain("memory sub-system is unknown, please correct it");
+        output.shouldNotContain("Threads");
+        output.shouldNotContain("CodeCache");
+        output.shouldNotContain("MetaspaceAux");
+        output.shouldHaveExitValue(1);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/gc/ergonomics/TestDynamicNumberOfGCThreads.java	Wed Nov 16 12:32:54 2016 -0800
@@ -0,0 +1,79 @@
+/*
+ * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+/*
+ * @test TestDynamicNumberOfGCThreads
+ * @bug 8017462
+ * @summary Ensure that UseDynamicNumberOfGCThreads runs
+ * @requires vm.gc=="null"
+ * @key gc
+ * @library /testlibrary
+ */
+
+import com.oracle.java.testlibrary.ProcessTools;
+import com.oracle.java.testlibrary.OutputAnalyzer;
+
+public class TestDynamicNumberOfGCThreads {
+  public static void main(String[] args) throws Exception {
+
+    testDynamicNumberOfGCThreads("UseConcMarkSweepGC");
+
+    testDynamicNumberOfGCThreads("UseG1GC");
+
+    testDynamicNumberOfGCThreads("UseParallelGC");
+  }
+
+  private static void verifyDynamicNumberOfGCThreads(OutputAnalyzer output) {
+    output.shouldHaveExitValue(0); // test should run succesfully
+    output.shouldContain("new_active_workers");
+  }
+
+  private static void testDynamicNumberOfGCThreads(String gcFlag) throws Exception {
+    // UseDynamicNumberOfGCThreads and TraceDynamicGCThreads enabled
+    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()));
+  }
+
+  static class GCTest {
+    private static byte[] garbage;
+    public static void main(String [] args) {
+      System.out.println("Creating garbage");
+      // create 128MB of garbage. This should result in at least one GC
+      for (int i = 0; i < 1024; i++) {
+        garbage = new byte[128 * 1024];
+      }
+      System.out.println("Done");
+    }
+  }
+}
--- a/test/runtime/NMT/VirtualAllocCommitUncommitRecommit.java	Wed Nov 09 14:41:57 2016 -0800
+++ b/test/runtime/NMT/VirtualAllocCommitUncommitRecommit.java	Wed Nov 16 12:32:54 2016 -0800
@@ -42,8 +42,8 @@
 
     public static void main(String args[]) throws Exception {
         OutputAnalyzer output;
-        long commitSize = 4 * 1024; // 4KB
-        long reserveSize = 1024 * 1024; // 1024KB
+        long commitSize = 128 * 1024; // 128KB
+        long reserveSize = 4 * 1024 * 1024; // 4096KB
         long addr;
 
         String pid = Integer.toString(ProcessTools.getProcessId());
@@ -62,11 +62,11 @@
                 "VM.native_memory", "detail" });
 
         output = new OutputAnalyzer(pb.start());
-        output.shouldContain("Test (reserved=1024KB, committed=0KB)");
+        output.shouldContain("Test (reserved=4096KB, committed=0KB)");
         if (has_nmt_detail) {
             output.shouldMatch("\\[0x[0]*" + Long.toHexString(addr) + " - 0x[0]*"
                     + Long.toHexString(addr + reserveSize)
-                    + "\\] reserved 1024KB for Test");
+                    + "\\] reserved 4096KB for Test");
         }
 
         long addrA = addr;
@@ -83,24 +83,24 @@
         wb.NMTCommitMemory(addrD, commitSize);
 
         output = new OutputAnalyzer(pb.start());
-        output.shouldContain("Test (reserved=1024KB, committed=16KB)");
+        output.shouldContain("Test (reserved=4096KB, committed=512KB)");
 
         if (has_nmt_detail) {
             output.shouldMatch("\\[0x[0]*" + Long.toHexString(addr) + " - 0x[0]*"
                     + Long.toHexString(addr + reserveSize)
-                    + "\\] reserved 1024KB for Test");
+                    + "\\] reserved 4096KB for Test");
         }
         // uncommit BC
         wb.NMTUncommitMemory(addrB, commitSize);
         wb.NMTUncommitMemory(addrC, commitSize);
 
         output = new OutputAnalyzer(pb.start());
-        output.shouldContain("Test (reserved=1024KB, committed=8KB)");
+        output.shouldContain("Test (reserved=4096KB, committed=256KB)");
 
         if (has_nmt_detail) {
             output.shouldMatch("\\[0x[0]*" + Long.toHexString(addr) + " - 0x[0]*"
                     + Long.toHexString(addr + reserveSize)
-                    + "\\] reserved 1024KB for Test");
+                    + "\\] reserved 4096KB for Test");
         }
 
         // commit EF
@@ -108,22 +108,22 @@
         wb.NMTCommitMemory(addrF, commitSize);
 
         output = new OutputAnalyzer(pb.start());
-        output.shouldContain("Test (reserved=1024KB, committed=16KB)");
+        output.shouldContain("Test (reserved=4096KB, committed=512KB)");
         if (has_nmt_detail) {
             output.shouldMatch("\\[0x[0]*" + Long.toHexString(addr) + " - 0x[0]*"
                     + Long.toHexString(addr + reserveSize)
-                    + "\\] reserved 1024KB for Test");
+                    + "\\] reserved 4096KB for Test");
         }
 
         // uncommit A
         wb.NMTUncommitMemory(addrA, commitSize);
 
         output = new OutputAnalyzer(pb.start());
-        output.shouldContain("Test (reserved=1024KB, committed=12KB)");
+        output.shouldContain("Test (reserved=4096KB, committed=384KB)");
         if (has_nmt_detail) {
             output.shouldMatch("\\[0x[0]*" + Long.toHexString(addr) + " - 0x[0]*"
                     + Long.toHexString(addr + reserveSize)
-                    + "\\] reserved 1024KB for Test");
+                    + "\\] reserved 4096KB for Test");
         }
 
         // commit ABC
@@ -132,11 +132,11 @@
         wb.NMTCommitMemory(addrC, commitSize);
 
         output = new OutputAnalyzer(pb.start());
-        output.shouldContain("Test (reserved=1024KB, committed=24KB)");
+        output.shouldContain("Test (reserved=4096KB, committed=768KB)");
         if (has_nmt_detail) {
             output.shouldMatch("\\[0x[0]*" + Long.toHexString(addr) + " - 0x[0]*"
                     + Long.toHexString(addr + reserveSize)
-                    + "\\] reserved 1024KB for Test");
+                    + "\\] reserved 4096KB for Test");
         }
 
         // uncommit ABCDEF
@@ -148,11 +148,11 @@
         wb.NMTUncommitMemory(addrF, commitSize);
 
         output = new OutputAnalyzer(pb.start());
-        output.shouldContain("Test (reserved=1024KB, committed=0KB)");
+        output.shouldContain("Test (reserved=4096KB, committed=0KB)");
         if (has_nmt_detail) {
             output.shouldMatch("\\[0x[0]*" + Long.toHexString(addr) + " - 0x[0]*"
                     + Long.toHexString(addr + reserveSize)
-                    + "\\] reserved 1024KB for Test");
+                    + "\\] reserved 4096KB for Test");
         }
 
         // release
@@ -160,6 +160,6 @@
         output = new OutputAnalyzer(pb.start());
         output.shouldNotContain("Test (reserved=");
         output.shouldNotMatch("\\[0x[0]*" + Long.toHexString(addr) + " - 0x[0]*"
-                + Long.toHexString(addr + reserveSize) + "\\] reserved 1024KB for Test");
+                + Long.toHexString(addr + reserveSize) + "\\] reserved 4096KB for Test");
     }
 }
--- a/test/testlibrary/whitebox/sun/hotspot/WhiteBox.java	Wed Nov 09 14:41:57 2016 -0800
+++ b/test/testlibrary/whitebox/sun/hotspot/WhiteBox.java	Wed Nov 16 12:32:54 2016 -0800
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, 2015, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012, 2016, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -233,4 +233,6 @@
     return offset;
   }
 
+  // Class Data Sharing
+  public native boolean isSharedClass(Class<?> c);
 }