!40 updated to aarch64-shenandoah-jdk8u272-b10

From: @jdkboy
Reviewed-by: @jvmboy
Signed-off-by: @jvmboy
This commit is contained in:
openeuler-ci-bot 2020-10-24 13:57:04 +08:00 committed by Gitee
commit 74b05accf2
38 changed files with 3490 additions and 654 deletions

View File

@ -0,0 +1,26 @@
From 5462717718cd9d3bed0d866ae47fe5ab9fdcf5e6 Mon Sep 17 00:00:00 2001
Date: Fri, 28 Aug 2020 15:02:16 +0800
Subject: [PATCH] 6896810: Pin.java fails with OOME during System.out.println
Summary: <java.lang>: Pin.java fails with OOME during System.out.println
LLT: jdk8u/jdk/test/java/lang/ref/SoftReference/Pin.java
Bug url: https://bugs.openjdk.java.net/browse/JDK-6896810 huaweijdk/jdk8u-dev#2472
---
jdk/test/java/lang/ref/SoftReference/Pin.java | 1 +
1 file changed, 1 insertion(+)
diff --git a/jdk/test/java/lang/ref/SoftReference/Pin.java b/jdk/test/java/lang/ref/SoftReference/Pin.java
index dbdf9be1b..38cd56da2 100644
--- a/jdk/test/java/lang/ref/SoftReference/Pin.java
+++ b/jdk/test/java/lang/ref/SoftReference/Pin.java
@@ -76,6 +76,7 @@ public class Pin {
Thread.sleep(100); // yield, for what it's worth
}
} catch (OutOfMemoryError e) {
+ chain = null; // Free memory for further work.
System.err.println("Got OutOfMemoryError, as expected.");
}
--
2.12.3

View File

@ -1,87 +0,0 @@
diff --git a/jdk/src/share/classes/sun/security/ssl/RandomCookie.java b/jdk/src/share/classes/sun/security/ssl/RandomCookie.java
index 5f414c408..ce27f0df4 100644
--- a/jdk/src/share/classes/sun/security/ssl/RandomCookie.java
+++ b/jdk/src/share/classes/sun/security/ssl/RandomCookie.java
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 1996, 2007, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1996, 2016, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -41,21 +41,8 @@ final class RandomCookie {
byte random_bytes[]; // exactly 32 bytes
RandomCookie(SecureRandom generator) {
- long temp = System.currentTimeMillis() / 1000;
- int gmt_unix_time;
- if (temp < Integer.MAX_VALUE) {
- gmt_unix_time = (int) temp;
- } else {
- gmt_unix_time = Integer.MAX_VALUE; // Whoops!
- }
-
random_bytes = new byte[32];
generator.nextBytes(random_bytes);
-
- random_bytes[0] = (byte)(gmt_unix_time >> 24);
- random_bytes[1] = (byte)(gmt_unix_time >> 16);
- random_bytes[2] = (byte)(gmt_unix_time >> 8);
- random_bytes[3] = (byte)gmt_unix_time;
}
RandomCookie(HandshakeInStream m) throws IOException {
@@ -68,22 +55,15 @@ final class RandomCookie {
}
void print(PrintStream s) {
- int i, gmt_unix_time;
-
- gmt_unix_time = random_bytes[0] << 24;
- gmt_unix_time += random_bytes[1] << 16;
- gmt_unix_time += random_bytes[2] << 8;
- gmt_unix_time += random_bytes[3];
-
- s.print("GMT: " + gmt_unix_time + " ");
- s.print("bytes = { ");
-
- for (i = 4; i < 32; i++) {
- if (i != 4) {
- s.print(", ");
+ s.print("random_bytes = {");
+ for (int i = 0; i < 32; i++) {
+ int k = random_bytes[i] & 0xFF;
+ if (i != 0) {
+ s.print(' ');
}
- s.print(random_bytes[i] & 0x0ff);
+ s.print(Utilities.hexDigits[k >>> 4]);
+ s.print(Utilities.hexDigits[k & 0xf]);
}
- s.println(" }");
+ s.println("}");
}
}
diff --git a/jdk/src/share/classes/sun/security/ssl/Utilities.java b/jdk/src/share/classes/sun/security/ssl/Utilities.java
index aefb02c9a..9b267f6e1 100644
--- a/jdk/src/share/classes/sun/security/ssl/Utilities.java
+++ b/jdk/src/share/classes/sun/security/ssl/Utilities.java
@@ -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
@@ -33,6 +33,11 @@ import sun.net.util.IPAddressUtil;
* A utility class to share the static methods.
*/
final class Utilities {
+ /**
+ * hex digits
+ */
+ static final char[] hexDigits = "0123456789ABCDEF".toCharArray();
+
/**
* Puts {@code hostname} into the {@code serverNames} list.
* <P>

View File

@ -0,0 +1,39 @@
From d4fc164f500d86fcec9302d9b71a830c34888680 Mon Sep 17 00:00:00 2001
Date: Wed, 12 Aug 2020 15:26:59 +0000
Subject: [PATCH] 8048210 8056152: fix assert fail for an InnocuousThread
Summary: <java.lang>: fix assert fail for an InnocuousThread
LLT: jdk8u/jdk/test/java/rmi/transport/pinLastArguments/PinLastArguments.java
Bug url: https://bugs.openjdk.java.net/browse/JDK-8048210 https://bugs.openjdk.java.net/browse/JDK-8056152
---
jdk/src/share/classes/sun/misc/InnocuousThread.java | 7 +------
1 file changed, 1 insertion(+), 6 deletions(-)
diff --git a/jdk/src/share/classes/sun/misc/InnocuousThread.java b/jdk/src/share/classes/sun/misc/InnocuousThread.java
index 3acd9424c..e585a9c0b 100644
--- a/jdk/src/share/classes/sun/misc/InnocuousThread.java
+++ b/jdk/src/share/classes/sun/misc/InnocuousThread.java
@@ -70,6 +70,7 @@ public final class InnocuousThread extends Thread {
public InnocuousThread(Runnable target) {
super(INNOCUOUSTHREADGROUP, target, newName());
UNSAFE.putOrderedObject(this, INHERITEDACCESSCONTROLCONTEXT, ACC);
+ UNSAFE.putOrderedObject(this, CONTEXTCLASSLOADER, ClassLoader.getSystemClassLoader());
eraseThreadLocals();
}
@@ -81,12 +82,6 @@ public final class InnocuousThread extends Thread {
}
@Override
- public ClassLoader getContextClassLoader() {
- // always report system class loader
- return ClassLoader.getSystemClassLoader();
- }
-
- @Override
public void setUncaughtExceptionHandler(UncaughtExceptionHandler x) {
// silently fail
}
--
2.12.3

View File

@ -1,12 +1,9 @@
From c2d7c271a60a6892bbbf7a2d585aa5b50c85bef1 Mon Sep 17 00:00:00 2001
From: sunjianye <sunjianye@huawei.com>
Date: Sat, 23 May 2020 17:40:00 +0800
Subject: [PATCH] 8080289 8040213 8189067: move the store out of the loop
DTS/AR: AR.SR.IREQ02373832.002.001
Summary: <superWord> : move the store out of the loop
LLT: NA
Patch Type: backport
Bug url: https://bugs.openjdk.java.net/browse/JDK-8080289 https://bugs.openjdk.java.net/browse/JDK-8040213 https://bugs.openjdk.java.net/browse/JDK-8189067
---
hotspot/src/share/vm/opto/loopnode.cpp | 2 +-

View File

@ -1,13 +1,10 @@
From e938b66397096f88ef40f4fc3522a543f938267d Mon Sep 17 00:00:00 2001
From: sunjianye <sunjianye@huawei.com>
Date: Sat, 23 May 2020 18:10:45 +0800
Subject: [PATCH] 8144993:Elide redundant memory barrier after AllocationNode
and JDK:8139758
DTS/AR: AR.SR.IREQ02373832.002.001
Summary: <C2> : Elide redundant memory barrier after AllocationNode
LLT: NA
Patch Type: backport
Bug url: https://bugs.openjdk.java.net/browse/JDK-8144993 https://bugs.openjdk.java.net/browse/JDK-8139758
---
hotspot/src/share/vm/opto/callnode.cpp | 18 ++++

View File

@ -1,180 +0,0 @@
From be0206e834bab370da41cf9ec9e6b9be710e1987 Mon Sep 17 00:00:00 2001
Date: Fri, 19 Apr 2019 17:40:19 +0000
Subject: [PATCH] 8148754: C2 loop unrolling fails due to unexpected graph shape
Summary: C2 loop unrolling fails due to unexpected graph shape
Bug url: https://bugs.openjdk.java.net/browse/JDK-8148754
---
hotspot/src/share/vm/opto/loopTransform.cpp | 44 ++++++++-------------
hotspot/src/share/vm/opto/loopnode.cpp | 36 +++++++++++++++++
hotspot/src/share/vm/opto/loopnode.hpp | 3 ++
hotspot/src/share/vm/opto/superword.cpp | 18 +++------
4 files changed, 61 insertions(+), 40 deletions(-)
diff --git a/hotspot/src/share/vm/opto/loopTransform.cpp b/hotspot/src/share/vm/opto/loopTransform.cpp
index e3637b652..f6783b910 100644
--- a/hotspot/src/share/vm/opto/loopTransform.cpp
+++ b/hotspot/src/share/vm/opto/loopTransform.cpp
@@ -1222,21 +1222,14 @@ void PhaseIdealLoop::do_unroll( IdealLoopTree *loop, Node_List &old_new, bool ad
Node *opaq = NULL;
if (adjust_min_trip) { // If not maximally unrolling, need adjustment
- // Search for zero-trip guard.
- assert( loop_head->is_main_loop(), "" );
- assert( ctrl->Opcode() == Op_IfTrue || ctrl->Opcode() == Op_IfFalse, "" );
- Node *iff = ctrl->in(0);
- assert( iff->Opcode() == Op_If, "" );
- Node *bol = iff->in(1);
- assert( bol->Opcode() == Op_Bool, "" );
- Node *cmp = bol->in(1);
- assert( cmp->Opcode() == Op_CmpI, "" );
- opaq = cmp->in(2);
- // Occasionally it's possible for a zero-trip guard Opaque1 node to be
- // optimized away and then another round of loop opts attempted.
- // We can not optimize this particular loop in that case.
- if (opaq->Opcode() != Op_Opaque1)
- return; // Cannot find zero-trip guard! Bail out!
+ // Check the shape of the graph at the loop entry. If an inappropriate
+ // graph shape is encountered, the compiler bails out loop unrolling;
+ // compilation of the method will still succeed.
+ if (!is_canonical_main_loop_entry(loop_head)) {
+ return;
+ }
+ // get a not shared opaque' node for Zero-trip test
+ opaq = ctrl->in(0)->in(1)->in(1)->in(2);
// Zero-trip test uses an 'opaque' node which is not shared.
assert(opaq->outcnt() == 1 && opaq->in(1) == limit, "");
}
@@ -1806,7 +1799,6 @@ void PhaseIdealLoop::do_range_check( IdealLoopTree *loop, Node_List &old_new ) {
#endif
assert(RangeCheckElimination, "");
CountedLoopNode *cl = loop->_head->as_CountedLoop();
- assert(cl->is_main_loop(), "");
// protect against stride not being a constant
if (!cl->stride_is_con())
@@ -1818,20 +1810,18 @@ void PhaseIdealLoop::do_range_check( IdealLoopTree *loop, Node_List &old_new ) {
// to not ever trip end tests
Node *main_limit = cl->limit();
+ // Check graph shape. Cannot optimize a loop if zero-trip
+ // Opaque1 node is optimized away and then another round
+ // of loop opts attempted.
+ if (!is_canonical_main_loop_entry(cl)) {
+ return;
+ }
+
// Need to find the main-loop zero-trip guard
Node *ctrl = cl->in(LoopNode::EntryControl);
- assert(ctrl->Opcode() == Op_IfTrue || ctrl->Opcode() == Op_IfFalse, "");
Node *iffm = ctrl->in(0);
- assert(iffm->Opcode() == Op_If, "");
- Node *bolzm = iffm->in(1);
- assert(bolzm->Opcode() == Op_Bool, "");
- Node *cmpzm = bolzm->in(1);
- assert(cmpzm->is_Cmp(), "");
- Node *opqzm = cmpzm->in(2);
- // Can not optimize a loop if zero-trip Opaque1 node is optimized
- // away and then another round of loop opts attempted.
- if (opqzm->Opcode() != Op_Opaque1)
- return;
+ // get the zero-trip Opaque1 node for testing the main limits
+ Node *opqzm = iffm->in(1)->in(1)->in(2);
assert(opqzm->in(1) == main_limit, "do not understand situation");
// Find the pre-loop limit; we will expand it's iterations to
diff --git a/hotspot/src/share/vm/opto/loopnode.cpp b/hotspot/src/share/vm/opto/loopnode.cpp
index 37c56681d..e2c0645cf 100644
--- a/hotspot/src/share/vm/opto/loopnode.cpp
+++ b/hotspot/src/share/vm/opto/loopnode.cpp
@@ -3284,6 +3284,42 @@ Node* PhaseIdealLoop::compute_lca_of_uses(Node* n, Node* early, bool verify) {
return LCA;
}
+// Check the shape of the graph at the loop entry. In some cases,
+// the shape of the graph does not match the shape outlined below.
+// That is caused by the Opaque1 node "protecting" the shape of
+// the graph being removed by, for example, the IGVN performed
+// in PhaseIdealLoop::build_and_optimize().
+//
+// After the Opaque1 node has been removed, optimizations (e.g., split-if,
+// loop unswitching, and IGVN, or a combination of them) can freely change
+// the graph's shape. As a result, the graph shape outlined below cannot
+// be guaranteed anymore.
+bool PhaseIdealLoop::is_canonical_main_loop_entry(CountedLoopNode* cl) {
+ assert(cl->is_main_loop(), "check should be applied to main loops");
+ Node* ctrl = cl->in(LoopNode::EntryControl);
+ if (ctrl == NULL || (!ctrl->is_IfTrue() && !ctrl->is_IfFalse())) {
+ return false;
+ }
+ Node* iffm = ctrl->in(0);
+ if (iffm == NULL || !iffm->is_If()) {
+ return false;
+ }
+ Node* bolzm = iffm->in(1);
+ if (bolzm == NULL || !bolzm->is_Bool()) {
+ return false;
+ }
+ Node* cmpzm = bolzm->in(1);
+ if (cmpzm == NULL || !cmpzm->is_Cmp()) {
+ return false;
+ }
+ // get the compare node, if null or not return false
+ Node* opqzm = cmpzm->in(2);
+ if (opqzm == NULL || opqzm->Opcode() != Op_Opaque1) {
+ return false;
+ }
+ return true;
+}
+
//------------------------------get_late_ctrl----------------------------------
// Compute latest legal control.
Node *PhaseIdealLoop::get_late_ctrl( Node *n, Node *early ) {
diff --git a/hotspot/src/share/vm/opto/loopnode.hpp b/hotspot/src/share/vm/opto/loopnode.hpp
index 150d1be0f..558b10504 100644
--- a/hotspot/src/share/vm/opto/loopnode.hpp
+++ b/hotspot/src/share/vm/opto/loopnode.hpp
@@ -621,6 +621,9 @@ private:
bool cast_incr_before_loop(Node* incr, Node* ctrl, Node* loop);
public:
+
+ static bool is_canonical_main_loop_entry(CountedLoopNode* cl);
+
bool has_node( Node* n ) const {
guarantee(n != NULL, "No Node.");
return _nodes[n->_idx] != NULL;
diff --git a/hotspot/src/share/vm/opto/superword.cpp b/hotspot/src/share/vm/opto/superword.cpp
index 0bc171b5c..a14210ee2 100644
--- a/hotspot/src/share/vm/opto/superword.cpp
+++ b/hotspot/src/share/vm/opto/superword.cpp
@@ -2209,21 +2209,13 @@ void SuperWord::align_initial_loop_index(MemNode* align_to_ref) {
//----------------------------get_pre_loop_end---------------------------
// Find pre loop end from main loop. Returns null if none.
CountedLoopEndNode* SuperWord::get_pre_loop_end(CountedLoopNode* cl) {
- Node* ctrl = cl->in(LoopNode::EntryControl);
- if (!ctrl->is_IfTrue() && !ctrl->is_IfFalse()) return NULL;
- Node* iffm = ctrl->in(0);
- if (!iffm->is_If()) return NULL;
- Node* bolzm = iffm->in(1);
- if (!bolzm->is_Bool()) return NULL;
- Node* cmpzm = bolzm->in(1);
- if (!cmpzm->is_Cmp()) return NULL;
- Node* opqzm = cmpzm->in(2);
- // Can not optimize a loop if zero-trip Opaque1 node is optimized
- // away and then another round of loop opts attempted.
- if (opqzm->Opcode() != Op_Opaque1) {
+ // The loop cannot be optimized if the graph shape at
+ // the loop entry is inappropriate.
+ if (!PhaseIdealLoop::is_canonical_main_loop_entry(cl)) {
return NULL;
}
- Node* p_f = iffm->in(0);
+
+ Node* p_f = cl->in(LoopNode::EntryControl)->in(0)->in(0);
if (!p_f->is_IfFalse()) return NULL;
if (!p_f->in(0)->is_CountedLoopEnd()) return NULL;
CountedLoopEndNode* pre_end = p_f->in(0)->as_CountedLoopEnd();
--
2.19.0

View File

@ -1,93 +0,0 @@
From bf24abe7a9499638a43dfd03fecfbfb763430a63 Mon Sep 17 00:00:00 2001
Date: Thu, 27 Jun 2019 11:24:39 +0000
Subject: [PATCH] Backport of JDK-8151788
summary: NullPointerException from ntlm.Client.type3
LLT:
Bug url: https://bugs.openjdk.java.net/browse/JDK-8151788
---
.../classes/com/sun/security/ntlm/NTLM.java | 2 +-
.../www/protocol/http/NULLTargetInfoTest.java | 58 +++++++++++++++++++
2 files changed, 59 insertions(+), 1 deletion(-)
create mode 100644 jdk/test/sun/net/www/protocol/http/NULLTargetInfoTest.java
diff --git a/jdk/src/share/classes/com/sun/security/ntlm/NTLM.java b/jdk/src/share/classes/com/sun/security/ntlm/NTLM.java
index da18e2199a..249cd226c4 100644
--- a/jdk/src/share/classes/com/sun/security/ntlm/NTLM.java
+++ b/jdk/src/share/classes/com/sun/security/ntlm/NTLM.java
@@ -167,7 +167,7 @@ class NTLM {
byte[] readSecurityBuffer(int offset) throws NTLMException {
int pos = readInt(offset+4);
- if (pos == 0) return null;
+ if (pos == 0) return new byte[0];
try {
return Arrays.copyOfRange(
internal, pos, pos + readShort(offset));
diff --git a/jdk/test/sun/net/www/protocol/http/NULLTargetInfoTest.java b/jdk/test/sun/net/www/protocol/http/NULLTargetInfoTest.java
new file mode 100644
index 0000000000..d8e88554f8
--- /dev/null
+++ b/jdk/test/sun/net/www/protocol/http/NULLTargetInfoTest.java
@@ -0,0 +1,58 @@
+/*
+ * 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 8151788
+ * @summary NullPointerException from ntlm.Client.type3
+ * @modules java.base/com.sun.security.ntlm
+ * @run main NULLTargetInfoTest
+ */
+import com.sun.security.ntlm.Client;
+
+public class NULLTargetInfoTest {
+
+ public static void main(String[] args) throws Exception {
+ Client c = new Client(null, "host", "user", "domain", "pass".toCharArray());
+ c.type1();
+ // this input does have the 0x800000 bit(NTLMSSP_NEGOTIATE_TARGET_INFO) set
+ // but after offset 40 all eight bytes are all zero which means there is no
+ // security buffer for target info.
+ byte[] type2 = hex(
+ "4E 54 4C 4D 53 53 50 00 02 00 00 00 00 00 00 00"
+ + "00 00 00 00 05 82 89 00 0B 87 81 B6 2D 6E 8B C1"
+ + "00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00");
+ byte[] nonce = new byte[10];
+ c.type3(type2, nonce);
+ }
+
+ private static byte[] hex(String str) {
+ str = str.replaceAll("\\s", "");
+ byte[] response = new byte[str.length() / 2];
+ int index = 0;
+ for (int i = 0; i < str.length(); i += 2) {
+ response[index++] = Integer.valueOf(str.substring(i, i + 2), 16).byteValue();
+ }
+ return response;
+ }
+}
--
2.19.0-rc1

View File

@ -0,0 +1,257 @@
From c10681e2567e34426759a73a7af8fe6809a8db09 Mon Sep 17 00:00:00 2001
Date: Fri, 28 Aug 2020 09:51:37 +0800
Subject: [PATCH] 8160425: Vectorization with signalling NaN returns wrong
result
Summary: <hotspot>: Should not use doubles/floats for vector constants in the C code
LLT:
Bug url: https://bugs.openjdk.java.net/browse/JDK-8160425
---
hotspot/src/cpu/sparc/vm/sparc.ad | 10 ++-
hotspot/src/cpu/x86/vm/x86.ad | 10 ++-
hotspot/src/share/vm/asm/assembler.hpp | 9 +++
hotspot/src/share/vm/opto/compile.cpp | 3 +
hotspot/src/share/vm/opto/compile.hpp | 9 +++
.../test/compiler/vectorization/TestNaNVector.java | 84 ++++++++++++++++++++++
6 files changed, 113 insertions(+), 12 deletions(-)
create mode 100644 hotspot/test/compiler/vectorization/TestNaNVector.java
diff --git a/hotspot/src/cpu/sparc/vm/sparc.ad b/hotspot/src/cpu/sparc/vm/sparc.ad
index 20ec462a7..c8763c411 100644
--- a/hotspot/src/cpu/sparc/vm/sparc.ad
+++ b/hotspot/src/cpu/sparc/vm/sparc.ad
@@ -720,7 +720,7 @@ intptr_t get_offset_from_base_2(const MachNode* n, const TypePtr* atype, int dis
return offset;
}
-static inline jdouble replicate_immI(int con, int count, int width) {
+static inline jlong replicate_immI(int con, int count, int width) {
// Load a constant replicated "count" times with width "width"
assert(count*width == 8 && width <= 4, "sanity");
int bit_width = width * 8;
@@ -729,17 +729,15 @@ static inline jdouble replicate_immI(int con, int count, int width) {
for (int i = 0; i < count - 1; i++) {
val |= (val << bit_width);
}
- jdouble dval = *((jdouble*) &val); // coerce to double type
- return dval;
+ return val;
}
-static inline jdouble replicate_immF(float con) {
+static inline jlong replicate_immF(float con) {
// Replicate float con 2 times and pack into vector.
int val = *((int*)&con);
jlong lval = val;
lval = (lval << 32) | (lval & 0xFFFFFFFFl);
- jdouble dval = *((jdouble*) &lval); // coerce to double type
- return dval;
+ return lval;
}
// Standard Sparc opcode form2 field breakdown
diff --git a/hotspot/src/cpu/x86/vm/x86.ad b/hotspot/src/cpu/x86/vm/x86.ad
index 36d6d96ae..48a0b95b4 100644
--- a/hotspot/src/cpu/x86/vm/x86.ad
+++ b/hotspot/src/cpu/x86/vm/x86.ad
@@ -856,7 +856,7 @@ static int vec_spill_helper(CodeBuffer *cbuf, bool do_size, bool is_load,
return 5+offset_size;
}
-static inline jfloat replicate4_imm(int con, int width) {
+static inline jint replicate4_imm(int con, int width) {
// Load a constant of "width" (in bytes) and replicate it to fill 32bit.
assert(width == 1 || width == 2, "only byte or short types here");
int bit_width = width * 8;
@@ -866,11 +866,10 @@ static inline jfloat replicate4_imm(int con, int width) {
val |= (val << bit_width);
bit_width <<= 1;
}
- jfloat fval = *((jfloat*) &val); // coerce to float type
- return fval;
+ return val;
}
-static inline jdouble replicate8_imm(int con, int width) {
+static inline jlong replicate8_imm(int con, int width) {
// Load a constant of "width" (in bytes) and replicate it to fill 64bit.
assert(width == 1 || width == 2 || width == 4, "only byte, short or int types here");
int bit_width = width * 8;
@@ -880,8 +879,7 @@ static inline jdouble replicate8_imm(int con, int width) {
val |= (val << bit_width);
bit_width <<= 1;
}
- jdouble dval = *((jdouble*) &val); // coerce to double type
- return dval;
+ return val;
}
#ifndef PRODUCT
diff --git a/hotspot/src/share/vm/asm/assembler.hpp b/hotspot/src/share/vm/asm/assembler.hpp
index 889dd361d..ec72bc3a1 100644
--- a/hotspot/src/share/vm/asm/assembler.hpp
+++ b/hotspot/src/share/vm/asm/assembler.hpp
@@ -368,6 +368,15 @@ class AbstractAssembler : public ResourceObj {
//
// We must remember the code section (insts or stubs) in c1
// so we can reset to the proper section in end_a_const().
+ address int_constant(jint c) {
+ CodeSection* c1 = _code_section;
+ address ptr = start_a_const(sizeof(c), sizeof(c));
+ if (ptr != NULL) {
+ emit_int32(c);
+ end_a_const(c1);
+ }
+ return ptr;
+ }
address long_constant(jlong c) {
CodeSection* c1 = _code_section;
address ptr = start_a_const(sizeof(c), sizeof(c));
diff --git a/hotspot/src/share/vm/opto/compile.cpp b/hotspot/src/share/vm/opto/compile.cpp
index 8e14f1d5a..34e97286e 100644
--- a/hotspot/src/share/vm/opto/compile.cpp
+++ b/hotspot/src/share/vm/opto/compile.cpp
@@ -3739,6 +3739,7 @@ bool Compile::Constant::operator==(const Constant& other) {
if (can_be_reused() != other.can_be_reused()) return false;
// For floating point values we compare the bit pattern.
switch (type()) {
+ case T_INT:
case T_FLOAT: return (_v._value.i == other._v._value.i);
case T_LONG:
case T_DOUBLE: return (_v._value.j == other._v._value.j);
@@ -3753,6 +3754,7 @@ bool Compile::Constant::operator==(const Constant& other) {
static int type_to_size_in_bytes(BasicType t) {
switch (t) {
+ case T_INT: return sizeof(jint );
case T_LONG: return sizeof(jlong );
case T_FLOAT: return sizeof(jfloat );
case T_DOUBLE: return sizeof(jdouble);
@@ -3821,6 +3823,7 @@ void Compile::ConstantTable::emit(CodeBuffer& cb) {
Constant con = _constants.at(i);
address constant_addr = NULL;
switch (con.type()) {
+ case T_INT: constant_addr = _masm.int_constant( con.get_jint() ); break;
case T_LONG: constant_addr = _masm.long_constant( con.get_jlong() ); break;
case T_FLOAT: constant_addr = _masm.float_constant( con.get_jfloat() ); break;
case T_DOUBLE: constant_addr = _masm.double_constant(con.get_jdouble()); break;
diff --git a/hotspot/src/share/vm/opto/compile.hpp b/hotspot/src/share/vm/opto/compile.hpp
index e4985acc7..60da8587b 100644
--- a/hotspot/src/share/vm/opto/compile.hpp
+++ b/hotspot/src/share/vm/opto/compile.hpp
@@ -203,6 +203,7 @@ class Compile : public Phase {
BasicType type() const { return _type; }
+ jint get_jint() const { return _v._value.i; }
jlong get_jlong() const { return _v._value.j; }
jfloat get_jfloat() const { return _v._value.f; }
jdouble get_jdouble() const { return _v._value.d; }
@@ -259,6 +260,14 @@ class Compile : public Phase {
Constant add(MachConstantNode* n, BasicType type, jvalue value);
Constant add(Metadata* metadata);
Constant add(MachConstantNode* n, MachOper* oper);
+ Constant add(MachConstantNode* n, jint i) {
+ jvalue value; value.i = i;
+ return add(n, T_INT, value);
+ }
+ Constant add(MachConstantNode* n, jlong j) {
+ jvalue value; value.j = j;
+ return add(n, T_LONG, value);
+ }
Constant add(MachConstantNode* n, jfloat f) {
jvalue value; value.f = f;
return add(n, T_FLOAT, value);
diff --git a/hotspot/test/compiler/vectorization/TestNaNVector.java b/hotspot/test/compiler/vectorization/TestNaNVector.java
new file mode 100644
index 000000000..302657951
--- /dev/null
+++ b/hotspot/test/compiler/vectorization/TestNaNVector.java
@@ -0,0 +1,84 @@
+/*
+ * 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 8160425
+ * @summary Test vectorization with a signalling NaN.
+ * @run main/othervm -XX:+IgnoreUnrecognizedVMOptions -XX:-OptimizeFill TestNaNVector
+ * @run main/othervm -XX:+IgnoreUnrecognizedVMOptions -XX:-OptimizeFill -XX:MaxVectorSize=4 TestNaNVector
+ */
+public class TestNaNVector {
+ private char[] array;
+ private static final int LEN = 1024;
+
+ public static void main(String args[]) {
+ TestNaNVector test = new TestNaNVector();
+ // Check double precision NaN
+ for (int i = 0; i < 10_000; ++i) {
+ test.vectorizeNaNDP();
+ }
+ System.out.println("Checking double precision Nan");
+ test.checkResult(0xfff7);
+
+ // Check single precision NaN
+ for (int i = 0; i < 10_000; ++i) {
+ test.vectorizeNaNSP();
+ }
+ System.out.println("Checking single precision Nan");
+ test.checkResult(0xff80);
+ }
+
+ public TestNaNVector() {
+ array = new char[LEN];
+ }
+
+ public void vectorizeNaNDP() {
+ // This loop will be vectorized and the array store will be replaced by
+ // a 64-bit vector store to four subsequent array elements. The vector
+ // should look like this '0xfff7fff7fff7fff7' and is read from the constant
+ // table. However, in floating point arithmetic this is a signalling NaN
+ // which may be converted to a quiet NaN when processed by the x87 FPU.
+ // If the signalling bit is set, the vector ends up in the constant table
+ // as '0xfffffff7fff7fff7' which leads to an incorrect result.
+ for (int i = 0; i < LEN; ++i) {
+ array[i] = 0xfff7;
+ }
+ }
+
+ public void vectorizeNaNSP() {
+ // Same as above but with single precision
+ for (int i = 0; i < LEN; ++i) {
+ array[i] = 0xff80;
+ }
+ }
+
+ public void checkResult(int expected) {
+ for (int i = 0; i < LEN; ++i) {
+ if (array[i] != expected) {
+ throw new RuntimeException("Invalid result: array[" + i + "] = " + (int)array[i] + " != " + expected);
+ }
+ }
+ }
+}
+
--
2.12.3

View File

@ -1,57 +0,0 @@
From e42367ab7ce5d66823ef32ea00dbc5e44e3b20d1 Mon Sep 17 00:00:00 2001
Date: Tue, 28 May 2019 21:38:21 +0000
Subject: [PATCH] 8161072: AArch64: jtreg compiler/uncommontrap/TestDeoptOOM failure
Summary:
Bug url: https://bugs.openjdk.java.net/browse/JDK-8161072
---
.../cpu/aarch64/vm/templateInterpreter_aarch64.cpp | 25 +++++++++++-----------
1 file changed, 12 insertions(+), 13 deletions(-)
diff --git a/hotspot/src/cpu/aarch64/vm/templateInterpreter_aarch64.cpp b/hotspot/src/cpu/aarch64/vm/templateInterpreter_aarch64.cpp
index 8dede4b74..566ddd173 100644
--- a/hotspot/src/cpu/aarch64/vm/templateInterpreter_aarch64.cpp
+++ b/hotspot/src/cpu/aarch64/vm/templateInterpreter_aarch64.cpp
@@ -223,19 +223,6 @@ address TemplateInterpreterGenerator::generate_deopt_entry_for(TosState state,
__ restore_locals();
__ restore_constant_pool_cache();
__ get_method(rmethod);
-
- // handle exceptions
- {
- Label L;
- __ ldr(rscratch1, Address(rthread, Thread::pending_exception_offset()));
- __ cbz(rscratch1, L);
- __ call_VM(noreg,
- CAST_FROM_FN_PTR(address,
- InterpreterRuntime::throw_pending_exception));
- __ should_not_reach_here();
- __ bind(L);
- }
-
__ get_dispatch();
// Calculate stack limit
@@ -253,6 +240,18 @@ address TemplateInterpreterGenerator::generate_deopt_entry_for(TosState state,
// NULL last_sp until next java call
__ str(zr, Address(rfp, frame::interpreter_frame_last_sp_offset * wordSize));
+ // handle exceptions
+ {
+ Label L;
+ __ ldr(rscratch1, Address(rthread, Thread::pending_exception_offset()));
+ __ cbz(rscratch1, L);
+ __ call_VM(noreg,
+ CAST_FROM_FN_PTR(address,
+ InterpreterRuntime::throw_pending_exception));
+ __ should_not_reach_here();
+ __ bind(L);
+ }
+
__ dispatch_next(state, step);
return entry;
}
--
2.12.3

View File

@ -1,26 +0,0 @@
From 26c54187c40901643d0cf65a985c98ddcee40bf0 Mon Sep 17 00:00:00 2001
Date: Fri, 19 Apr 2019 17:42:56 +0000
Subject: [PATCH] 8171537: aarch64: compiler/c1/Test6849574.java generates guarantee failure in C1
Bug url: https://bugs.openjdk.java.net/browse/JDK-8171537
---
hotspot/src/cpu/aarch64/vm/c1_LIRAssembler_aarch64.cpp | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/hotspot/src/cpu/aarch64/vm/c1_LIRAssembler_aarch64.cpp b/hotspot/src/cpu/aarch64/vm/c1_LIRAssembler_aarch64.cpp
index 6e225870e..e536ce649 100644
--- a/hotspot/src/cpu/aarch64/vm/c1_LIRAssembler_aarch64.cpp
+++ b/hotspot/src/cpu/aarch64/vm/c1_LIRAssembler_aarch64.cpp
@@ -3199,7 +3199,7 @@ void LIR_Assembler::peephole(LIR_List *lir) {
}
void LIR_Assembler::atomic_op(LIR_Code code, LIR_Opr src, LIR_Opr data, LIR_Opr dest, LIR_Opr tmp_op) {
- Address addr = as_Address(src->as_address_ptr(), noreg);
+ Address addr = as_Address(src->as_address_ptr(), as_reg(tmp_op));
BasicType type = src->type();
bool is_oop = type == T_OBJECT || type == T_ARRAY;
--
2.19.0

View File

@ -0,0 +1,69 @@
From c36e8cdc5f1175a3f2a771194434d76324d8cdbb Mon Sep 17 00:00:00 2001
Date: Fri, 17 Apr 2020 17:42:09 +0000
Subject: [PATCH] 8181503: Can't compile hotspot with c++11
Summary: <compile>: fix c++11 compiler issues
LLT: N/A
Bug url: https://bugs.openjdk.java.net/browse/JDK-8181503
---
hotspot/src/os_cpu/bsd_x86/vm/os_bsd_x86.cpp | 6 +++---
hotspot/src/share/vm/code/compiledIC.cpp | 2 +-
hotspot/src/share/vm/utilities/vmError.cpp | 2 +-
3 files changed, 5 insertions(+), 5 deletions(-)
diff --git a/hotspot/src/os_cpu/bsd_x86/vm/os_bsd_x86.cpp b/hotspot/src/os_cpu/bsd_x86/vm/os_bsd_x86.cpp
index 018feea1..935a16b5 100644
--- a/hotspot/src/os_cpu/bsd_x86/vm/os_bsd_x86.cpp
+++ b/hotspot/src/os_cpu/bsd_x86/vm/os_bsd_x86.cpp
@@ -281,11 +281,11 @@ PRAGMA_FORMAT_MUTE_WARNINGS_FOR_GCC
address os::current_stack_pointer() {
#if defined(__clang__) || defined(__llvm__)
register void *esp;
- __asm__("mov %%"SPELL_REG_SP", %0":"=r"(esp));
+ __asm__("mov %%" SPELL_REG_SP ", %0":"=r"(esp));
return (address) esp;
#elif defined(SPARC_WORKS)
register void *esp;
- __asm__("mov %%"SPELL_REG_SP", %0":"=r"(esp));
+ __asm__("mov %%" SPELL_REG_SP ", %0":"=r"(esp));
return (address) ((char*)esp + sizeof(long)*2);
#else
register void *esp __asm__ (SPELL_REG_SP);
@@ -368,7 +368,7 @@ frame os::get_sender_for_C_frame(frame* fr) {
intptr_t* _get_previous_fp() {
#if defined(SPARC_WORKS) || defined(__clang__) || defined(__llvm__)
register intptr_t **ebp;
- __asm__("mov %%"SPELL_REG_FP", %0":"=r"(ebp));
+ __asm__("mov %%" SPELL_REG_FP ", %0":"=r"(ebp));
#else
register intptr_t **ebp __asm__ (SPELL_REG_FP);
#endif
diff --git a/hotspot/src/share/vm/code/compiledIC.cpp b/hotspot/src/share/vm/code/compiledIC.cpp
index 63821c06..06794215 100644
--- a/hotspot/src/share/vm/code/compiledIC.cpp
+++ b/hotspot/src/share/vm/code/compiledIC.cpp
@@ -222,7 +222,7 @@ bool CompiledIC::set_to_megamorphic(CallInfo* call_info, Bytecodes::Code bytecod
assert(bytecode == Bytecodes::_invokeinterface, "");
int itable_index = call_info->itable_index();
entry = VtableStubs::find_itable_stub(itable_index);
- if (entry == false) {
+ if (entry == NULL) {
return false;
}
#ifdef ASSERT
diff --git a/hotspot/src/share/vm/utilities/vmError.cpp b/hotspot/src/share/vm/utilities/vmError.cpp
index e5aad6ff..23d495d9 100644
--- a/hotspot/src/share/vm/utilities/vmError.cpp
+++ b/hotspot/src/share/vm/utilities/vmError.cpp
@@ -399,7 +399,7 @@ void VMError::report(outputStream* st) {
STEP(15, "(printing type of error)")
- switch(_id) {
+ switch(static_cast<unsigned int>(_id)) {
case OOM_MALLOC_ERROR:
case OOM_MMAP_ERROR:
if (_size) {
--
2.19.0

View File

@ -1,28 +0,0 @@
diff --git a/hotspot/src/cpu/aarch64/vm/frame_aarch64.cpp b/hotspot/src/cpu/aarch64/vm/frame_aarch64.cpp
index 65a441240..1e534d3da 100644
--- a/hotspot/src/cpu/aarch64/vm/frame_aarch64.cpp
+++ b/hotspot/src/cpu/aarch64/vm/frame_aarch64.cpp
@@ -71,10 +71,20 @@ bool frame::safe_for_sender(JavaThread *thread) {
return false;
}
- // unextended sp must be within the stack and above or equal sp
- bool unextended_sp_safe = (unextended_sp < thread->stack_base()) &&
- (unextended_sp >= sp);
+ // When we are running interpreted code the machine stack pointer, SP, is
+ // set low enough so that the Java expression stack can grow and shrink
+ // without ever exceeding the machine stack bounds. So, ESP >= SP.
+ // When we call out of an interpreted method, SP is incremented so that
+ // the space between SP and ESP is removed. The SP saved in the callee's
+ // frame is the SP *before* this increment. So, when we walk a stack of
+ // interpreter frames the sender's SP saved in a frame might be less than
+ // the SP at the point of call.
+
+ // So unextended sp must be within the stack but we need not to check
+ // that unextended sp >= sp
+
+ bool unextended_sp_safe = (unextended_sp < thread->stack_base());
if (!unextended_sp_safe) {
return false;
}

View File

@ -1,40 +0,0 @@
From f9f94ca5422ae79bf4ed90f41b7698febc6bed24 Mon Sep 17 00:00:00 2001
Date: Fri, 12 Jul 2019 15:26:27 +0000
Subject: [PATCH] Backport of JDK-8203699: java/lang/invoke/SpecialInterfaceCall fails with SIGILL on aarch64
summary: Get super_klass value into r0 to make check in VerifyMethodHandles success
LLT: jdk/test/java/lang/invoke/lookup/TestDefenderMethodLookup.java
Bug url: https://bugs.openjdk.java.net/browse/JDK-8203699
---
.../src/cpu/aarch64/vm/macroAssembler_aarch64.cpp | 6 +-
1 files changed, 5 insertions(+), 1 deletion(-)
diff --git a/hotspot/src/cpu/aarch64/vm/macroAssembler_aarch64.cpp b/hotspot/src/cpu/aarch64/vm/macroAssembler_aarch64.cpp
index 42b732f37a..4659d628db 100644
--- a/hotspot/src/cpu/aarch64/vm/macroAssembler_aarch64.cpp
+++ b/hotspot/src/cpu/aarch64/vm/macroAssembler_aarch64.cpp
@@ -1208,7 +1208,6 @@ void MacroAssembler::check_klass_subtype_slow_path(Register sub_klass,
assert(sub_klass != r0, "killed reg"); // killed by mov(r0, super)
assert(sub_klass != r2, "killed reg"); // killed by lea(r2, &pst_counter)
- // Get super_klass value into r0 (even if it was in r5 or r2).
RegSet pushed_registers;
if (!IS_A_TEMP(r2)) pushed_registers += r2;
if (!IS_A_TEMP(r5)) pushed_registers += r5;
@@ -1219,6 +1218,11 @@ void MacroAssembler::check_klass_subtype_slow_path(Register sub_klass,
push(pushed_registers, sp);
+ // Get super_klass value into r0 (even if it was in r5 or r2)
+ if (super_klass != r0) {
+ mov(r0, super_klass);
+ }
+
#ifndef PRODUCT
mov(rscratch2, (address)&SharedRuntime::_partial_subtype_ctr);
Address pst_counter_addr(rscratch2);
diff --git a/jdk/test/java/lang/invoke/lookup/TestDefenderMethodLookup.java b/jdk/test/java/lang/invoke/lookup/TestDefenderMethodLookup.java
--
2.12.3

View File

@ -174,9 +174,9 @@ index 28dd5aad..271b33a5 100644
if (_cm->verbose_medium()) {
gclog_or_tty->print_cr("[%u] stolen " PTR_FORMAT " successfully",
_worker_id, p2i((void*) obj));
@@ -4605,7 +4605,7 @@ CMTask::CMTask(uint worker_id,
: _g1h(G1CollectedHeap::heap()),
@@ -4612,7 +4614,7 @@ CMTask::CMTask(uint worker_id,
_worker_id(worker_id), _cm(cm),
_objArray_processor(this),
_claimed(false),
- _nextMarkBitMap(NULL), _hash_seed(17),
+ _nextMarkBitMap(NULL),

View File

@ -1,13 +1,10 @@
From c1d5b7c044ba418848c98d36ec21358a1dac568e Mon Sep 17 00:00:00 2001
From: sunjianye <sunjianye@huawei.com>
Date: Sat, 23 May 2020 17:18:39 +0800
Subject: [PATCH] 8223504:improve performance of forall loops by better
inlining of "iterator()" methods
DTS/AR: AR.SR.IREQ02373832.002.001
Summary: <C2> : improve performance of forall loops by better inlining of "iterator()" methods
LLT: NA
Patch Type: backport
Bug url: https://bugs.openjdk.java.net/browse/JDK-8223504
---
hotspot/src/share/vm/classfile/systemDictionary.hpp | 3 +++

View File

@ -0,0 +1,30 @@
From 0a3958872fd70590976b185e086eec3f461b27c4 Mon Sep 17 00:00:00 2001
Date: Fri, 28 Aug 2020 09:28:23 +0800
Subject: [PATCH] 8231631: sun/net/ftp/FtpURLConnectionLeak.java fails
intermittently with NPE
Summary: <sun.net>: sun/net/www/ftptest/FtpCommandHandler.java is modified to handle EOF properly
LLT: jdk8u/jdk/test/sun/net/ftp/FtpURLConnectionLeak.java
Bug url: https://bugs.openjdk.java.net/browse/JDK-8231631 #2468
---
jdk/test/sun/net/www/ftptest/FtpCommandHandler.java | 4 ++++
1 file changed, 4 insertions(+)
diff --git a/jdk/test/sun/net/www/ftptest/FtpCommandHandler.java b/jdk/test/sun/net/www/ftptest/FtpCommandHandler.java
index 151b3df8e..f6c87d5a4 100644
--- a/jdk/test/sun/net/www/ftptest/FtpCommandHandler.java
+++ b/jdk/test/sun/net/www/ftptest/FtpCommandHandler.java
@@ -458,6 +458,10 @@ public class FtpCommandHandler extends Thread {
try {
str = in.readLine();
System.out.println("line: " + str);
+ if (str == null) {
+ System.out.println("EOF read from input");
+ break;
+ }
buf = new StringBuffer(str);
res = parseCmd(buf);
switch (res) {
--
2.12.3

View File

@ -0,0 +1,193 @@
From 3276b4d8d066703d3abc81e3a7815d1c03474af2 Mon Sep 17 00:00:00 2001
Date: Wed, 19 Aug 2020 17:43:46 +0000
Subject: [PATCH] 8243670:Unexpected test result caused by C2
MergeMemNode::Ideal
Summary: <c2>: <Unexpected test result caused by C2 MergeMemNode>
LLT: hotspot/test/compiler/c2/TestReplaceEquivPhis.java
Bug url: https://bugs.openjdk.java.net/browse/JDK-8243670
---
hotspot/src/share/vm/opto/cfgnode.cpp | 24 +++++++
hotspot/src/share/vm/opto/memnode.cpp | 20 +-----
hotspot/src/share/vm/opto/type.hpp | 7 ++
hotspot/test/compiler/c2/TestReplaceEquivPhis.java | 77 ++++++++++++++++++++++
4 files changed, 109 insertions(+), 19 deletions(-)
create mode 100644 hotspot/test/compiler/c2/TestReplaceEquivPhis.java
diff --git a/hotspot/src/share/vm/opto/cfgnode.cpp b/hotspot/src/share/vm/opto/cfgnode.cpp
index dd5a5ec41..f3d223fbd 100644
--- a/hotspot/src/share/vm/opto/cfgnode.cpp
+++ b/hotspot/src/share/vm/opto/cfgnode.cpp
@@ -1156,6 +1156,30 @@ Node *PhiNode::Identity( PhaseTransform *phase ) {
if (id != NULL) return id;
}
+ // Looking for phis with identical inputs. If we find one that has
+ // type TypePtr::BOTTOM, replace the current phi with the bottom phi.
+ if (phase->is_IterGVN() && type() == Type::MEMORY && adr_type() !=
+ TypePtr::BOTTOM && !adr_type()->is_known_instance()) {
+ uint phi_len = req();
+ Node* phi_reg = region();
+ for (DUIterator_Fast imax, i = phi_reg->fast_outs(imax); i < imax; i++) {
+ Node* u = phi_reg->fast_out(i);
+ if (u->is_Phi() && u->as_Phi()->type() == Type::MEMORY &&
+ u->adr_type() == TypePtr::BOTTOM && u->in(0) == phi_reg &&
+ u->req() == phi_len) {
+ for (uint j = 1; j < phi_len; j++) {
+ if (in(j) != u->in(j)) {
+ u = NULL;
+ break;
+ }
+ }
+ if (u != NULL) {
+ return u;
+ }
+ }
+ }
+ }
+
return this; // No identity
}
diff --git a/hotspot/src/share/vm/opto/memnode.cpp b/hotspot/src/share/vm/opto/memnode.cpp
index 68a13dbd8..f2a2ee6a2 100644
--- a/hotspot/src/share/vm/opto/memnode.cpp
+++ b/hotspot/src/share/vm/opto/memnode.cpp
@@ -4418,25 +4418,7 @@ Node *MergeMemNode::Ideal(PhaseGVN *phase, bool can_reshape) {
new_mem = old_mmem->memory_at(i);
}
// else preceding memory was not a MergeMem
-
- // replace equivalent phis (unfortunately, they do not GVN together)
- if (new_mem != NULL && new_mem != new_base &&
- new_mem->req() == phi_len && new_mem->in(0) == phi_reg) {
- if (new_mem->is_Phi()) {
- PhiNode* phi_mem = new_mem->as_Phi();
- for (uint i = 1; i < phi_len; i++) {
- if (phi_base->in(i) != phi_mem->in(i)) {
- phi_mem = NULL;
- break;
- }
- }
- if (phi_mem != NULL) {
- // equivalent phi nodes; revert to the def
- new_mem = new_base;
- }
- }
- }
-
+
// maybe store down a new value
Node* new_in = new_mem;
if (new_in == new_base) new_in = empty_mem;
diff --git a/hotspot/src/share/vm/opto/type.hpp b/hotspot/src/share/vm/opto/type.hpp
index a9352345e..321d79914 100644
--- a/hotspot/src/share/vm/opto/type.hpp
+++ b/hotspot/src/share/vm/opto/type.hpp
@@ -431,6 +431,8 @@ public:
return exact_kls != NULL;
}
+ virtual bool is_known_instance() const { return false; }
+
private:
// support arrays
static const Type* _zero_type[T_CONFLICT+1];
@@ -1332,6 +1334,11 @@ public:
return _ptrtype;
}
+ bool is_known_instance() const {
+ return _ptrtype->is_known_instance();
+ }
+
+
#ifndef PRODUCT
virtual void dump2( Dict &d, uint depth, outputStream *st ) const;
#endif
diff --git a/hotspot/test/compiler/c2/TestReplaceEquivPhis.java b/hotspot/test/compiler/c2/TestReplaceEquivPhis.java
new file mode 100644
index 000000000..d4c93b390
--- /dev/null
+++ b/hotspot/test/compiler/c2/TestReplaceEquivPhis.java
@@ -0,0 +1,77 @@
+/*
+ * Copyright (c) 2020, Huawei Technologies Co. Ltd. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please 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 8243670
+ * @summary Unexpected test result caused by C2 MergeMemNode::Ideal
+ *
+ * @run main/othervm -Xcomp -XX:-SplitIfBlocks
+ * -XX:CompileOnly=compiler.c2.TestReplaceEquivPhis::test
+ * -XX:-BackgroundCompilation compiler.c2.TestReplaceEquivPhis
+ */
+
+package compiler.c2;
+
+public class TestReplaceEquivPhis {
+
+ public static final int N = 400;
+ public static volatile int instanceCount = 0;
+ public int iFld = 0;
+ public static int iArrFld[] = new int[N];
+
+ public int test() {
+ int v = 0;
+ boolean bArr[] = new boolean[N];
+
+ for (int i = 1; i < 344; i++) {
+ iFld = i;
+ for (int j = 2; j <177 ; j++) {
+ v = iFld;
+ iFld = TestReplaceEquivPhis.instanceCount;
+ TestReplaceEquivPhis.iArrFld[i] = 0;
+ iFld += TestReplaceEquivPhis.instanceCount;
+ TestReplaceEquivPhis.iArrFld[i] = 0;
+ bArr[j] = false;
+ TestReplaceEquivPhis.instanceCount = 1;
+
+ for (int k = 1; k < 3; k++) {
+ // do nothing
+ }
+ }
+ }
+ return v;
+ }
+
+ public static void main(String[] args) {
+ TestReplaceEquivPhis obj = new TestReplaceEquivPhis();
+ for (int i = 0; i < 5; i++) {
+ int result = obj.test();
+ if (result != 2) {
+ throw new RuntimeException("Test failed.");
+ }
+ }
+ System.out.println("Test passed.");
+ }
+
+}
--
2.12.3

View File

@ -0,0 +1,747 @@
diff --git a/hotspot/src/share/vm/classfile/classFileParser.cpp b/hotspot/src/share/vm/classfile/classFileParser.cpp
index 6d62380..58d9116 100644
--- a/hotspot/src/share/vm/classfile/classFileParser.cpp
+++ b/hotspot/src/share/vm/classfile/classFileParser.cpp
@@ -3939,7 +3939,8 @@ instanceKlassHandle ClassFileParser::parseClassFile(Symbol* name,
#if INCLUDE_CDS
if (DumpLoadedClassList != NULL && cfs->source() != NULL && classlist_file->is_open()) {
// Only dump the classes that can be stored into CDS archive
- if (SystemDictionaryShared::is_sharing_possible(loader_data)) {
+ // unless AppCDS is enabled
+ if (_host_klass == NULL && SystemDictionaryShared::is_sharing_possible(loader_data)) {
if (name != NULL) {
ResourceMark rm(THREAD);
classlist_file->print_cr("%s", name->as_C_string());
diff --git a/hotspot/src/share/vm/classfile/classLoader.cpp b/hotspot/src/share/vm/classfile/classLoader.cpp
index b9f46df..c7c0f53 100644
--- a/hotspot/src/share/vm/classfile/classLoader.cpp
+++ b/hotspot/src/share/vm/classfile/classLoader.cpp
@@ -1203,8 +1203,8 @@ instanceKlassHandle ClassLoader::load_classfile(Symbol* h_name, TRAPS) {
h = context.record_result(classpath_index, e, result, THREAD);
} else {
- if (DumpSharedSpaces) {
- tty->print_cr("Preload Warning: Cannot find %s", class_name);
+ if (!UseAppCDS && DumpSharedSpaces) {
+ tty->print_cr("Preload Warning: Cannot find %s", class_name); // No need for AppCDS
}
}
diff --git a/hotspot/src/share/vm/classfile/systemDictionary.cpp b/hotspot/src/share/vm/classfile/systemDictionary.cpp
index 5c6b094..61140d3 100644
--- a/hotspot/src/share/vm/classfile/systemDictionary.cpp
+++ b/hotspot/src/share/vm/classfile/systemDictionary.cpp
@@ -175,6 +175,16 @@ bool SystemDictionary::is_ext_class_loader(Handle class_loader) {
return (class_loader->klass()->name() == vmSymbols::sun_misc_Launcher_ExtClassLoader());
}
+/**
+ * Returns true if the passed class loader is the application class loader.
+ */
+bool SystemDictionary::is_app_class_loader(Handle class_loader) {
+ if (class_loader.is_null()) {
+ return false;
+ }
+ return (class_loader->klass()->name() == vmSymbols::sun_misc_Launcher_AppClassLoader());
+}
+
// ----------------------------------------------------------------------------
// Resolving of classes
@@ -336,7 +346,8 @@ Klass* SystemDictionary::resolve_super_or_fail(Symbol* child_name,
// Bugs 4643874, 4715493
// compute_hash can have a safepoint
- ClassLoaderData* loader_data = class_loader_data(class_loader);
+ // class loader may be not registered yet, so use register_loader, which will return a valid classloaderData anyway.
+ ClassLoaderData* loader_data = register_loader(class_loader, CHECK_NULL);
unsigned int d_hash = dictionary()->compute_hash(child_name, loader_data);
int d_index = dictionary()->hash_to_index(d_hash);
unsigned int p_hash = placeholders()->compute_hash(child_name, loader_data);
@@ -526,7 +537,8 @@ instanceKlassHandle SystemDictionary::handle_parallel_super_load(
Handle protection_domain, Handle lockObject, TRAPS) {
instanceKlassHandle nh = instanceKlassHandle(); // null Handle
- ClassLoaderData* loader_data = class_loader_data(class_loader);
+ // class loader may be not registered yet, so use register_loader, which will return a valid classloaderData anyway.
+ ClassLoaderData* loader_data = register_loader(class_loader, CHECK_NULL);
unsigned int d_hash = dictionary()->compute_hash(name, loader_data);
int d_index = dictionary()->hash_to_index(d_hash);
unsigned int p_hash = placeholders()->compute_hash(name, loader_data);
@@ -1074,6 +1086,19 @@ Klass* SystemDictionary::parse_stream(Symbol* class_name,
return k();
}
+static char* convert_into_package_name(char* name) {
+ char* index = strrchr(name, '/');
+ if (index == NULL) {
+ return NULL;
+ } else {
+ *index = '\0'; // chop to just the package name
+ while ((index = strchr(name, '/')) != NULL) {
+ *index = '.'; // replace '/' with '.' in package name
+ }
+ return name;
+ }
+}
+
static bool is_prohibited_package_slow(Symbol* class_name) {
// Caller has ResourceMark
int length;
@@ -1147,12 +1172,9 @@ Klass* SystemDictionary::resolve_from_stream(Symbol* class_name,
// It is illegal to define classes in the "java." package from
// JVM_DefineClass or jni_DefineClass unless you're the bootclassloader
char* name = parsed_name->as_C_string();
- char* index = strrchr(name, '/');
- assert(index != NULL, "must be");
- *index = '\0'; // chop to just the package name
- while ((index = strchr(name, '/')) != NULL) {
- *index = '.'; // replace '/' with '.' in package name
- }
+ name = convert_into_package_name(name);
+ assert(name != NULL, "must be");
+
const char* fmt = "Prohibited package name: %s";
size_t len = strlen(fmt) + strlen(name);
char* message = NEW_RESOURCE_ARRAY(char, len);
@@ -1217,12 +1240,62 @@ Klass* SystemDictionary::find_shared_class(Symbol* class_name) {
instanceKlassHandle SystemDictionary::load_shared_class(
Symbol* class_name, Handle class_loader, TRAPS) {
- instanceKlassHandle ik (THREAD, find_shared_class(class_name));
- // Make sure we only return the boot class for the NULL classloader.
- if (ik.not_null() &&
- SharedClassUtil::is_shared_boot_class(ik()) && class_loader.is_null()) {
- Handle protection_domain;
- return load_shared_class(ik, class_loader, protection_domain, THREAD);
+ if (!(class_loader.is_null() || SystemDictionary::is_app_class_loader(class_loader) ||
+ SystemDictionary::is_ext_class_loader(class_loader))) {
+ return instanceKlassHandle();
+ }
+
+ instanceKlassHandle ik (THREAD, find_shared_class(class_name)); // InstanceKlass is find with null class loader.
+ if (ik.not_null()) {
+ if (!UseAppCDS) {
+ // CDS logic
+ if (SharedClassUtil::is_shared_boot_class(ik()) && class_loader.is_null()) {
+ // CDS record boot class load index.
+ Handle protection_domain;
+ return load_shared_class(ik, class_loader, protection_domain, THREAD);
+ }
+ } else {
+ // AppCDS logic. Only use null loader only to load classes that
+ // have been dumped by null loader. For non-null class loaders,
+ // either the class loader data is not initialized (but also not
+ // null) or the same class loader is used to load previously
+ // defined class
+ bool bFound = false;
+ if (class_loader.is_null()) {
+ // condition1: Bootstrap class loader loaded
+ bFound = (ik()->class_loader_data() == NULL || ik()->class_loader_data()->is_the_null_class_loader_data());
+ } else if (ik()->class_loader_data() != NULL) {
+ // condition2: App Class Loader
+ // condition3: ExtClass Loader
+ // Condition4: not fake class Loader, real one
+ bFound = ((ik->has_fake_loader_data_App() && SystemDictionary::is_app_class_loader(class_loader)) ||
+ (ik->has_fake_loader_data_Ext() && SystemDictionary::is_ext_class_loader(class_loader)) ||
+ (!ik->has_fake_loader_data() && ik()->class_loader() == class_loader()));
+ }
+ if (!bFound) {
+ return instanceKlassHandle();
+ }
+
+ // get protection domain for this class if not loaded by null class loader
+ if (class_loader.not_null()) {
+ ResourceMark rm(THREAD);
+ char* name = ik->name()->as_C_string();
+ Handle klass_name = java_lang_String::create_from_str(name, CHECK_0);
+ JavaValue result(T_OBJECT);
+
+ // ClassLoaderData* loader_data = ClassLoaderData::class_loader_data(class_loader());
+ JavaCalls::call_virtual(&result,
+ class_loader,
+ KlassHandle(THREAD, SystemDictionary::URLClassLoader_klass()),
+ vmSymbols::getProtectionDomainInternal_name(),
+ vmSymbols::getProtectionDomainInternal_signature(),
+ klass_name,
+ THREAD);
+ return load_shared_class(ik, class_loader, Handle(THREAD, (oop) result.get_jobject()), THREAD);
+ } else {
+ return load_shared_class(ik, class_loader, Handle(), THREAD);
+ }
+ }
}
return instanceKlassHandle();
}
@@ -1298,6 +1371,7 @@ instanceKlassHandle SystemDictionary::load_shared_class(instanceKlassHandle ik,
if (DumpLoadedClassList != NULL && classlist_file->is_open()) {
// Only dump the classes that can be stored into CDS archive
+ // unless AppCDS is enabled
if (SystemDictionaryShared::is_sharing_possible(loader_data)) {
ResourceMark rm(THREAD);
classlist_file->print_cr("%s", ik->name()->as_C_string());
@@ -1308,6 +1382,32 @@ instanceKlassHandle SystemDictionary::load_shared_class(instanceKlassHandle ik,
// notify a class loaded from shared object
ClassLoadingService::notify_class_loaded(InstanceKlass::cast(ik()),
true /* shared class */);
+
+ // register package for this class, if necessary
+ if (UseAppCDS && class_loader.not_null()) {
+
+ ResourceMark rm(THREAD);
+ char* name = ik->name()->as_C_string();
+ name = convert_into_package_name(name);
+ if (name != NULL) {
+ // not a default package
+ Handle package_name = java_lang_String::create_from_str(name, CHECK_0);
+ // The digital 4 is used only once, indicating the parameter number of
+ // the method invoked in JavaCalls::call_virtual
+ JavaCallArguments args(4);
+ args.push_oop(class_loader);
+ args.push_oop(package_name);
+ args.push_oop(Handle());
+ args.push_oop(Handle());
+ JavaValue result(T_VOID);
+ JavaCalls::call_virtual(&result,
+ KlassHandle(THREAD, SystemDictionary::URLClassLoader_klass()),
+ vmSymbols::definePackageInternal_name(),
+ vmSymbols::definePackageInternal_signature(),
+ &args,
+ CHECK_0);
+ }
+ }
}
return ik;
}
@@ -2167,7 +2267,6 @@ void SystemDictionary::update_dictionary(int d_index, unsigned int d_hash,
// yet and these will be ignored.
Klass* SystemDictionary::find_constrained_instance_or_array_klass(
Symbol* class_name, Handle class_loader, TRAPS) {
-
// First see if it has been loaded directly.
// Force the protection domain to be null. (This removes protection checks.)
Handle no_protection_domain;
diff --git a/hotspot/src/share/vm/classfile/systemDictionary.hpp b/hotspot/src/share/vm/classfile/systemDictionary.hpp
index 6f0b38a..cab7381 100644
--- a/hotspot/src/share/vm/classfile/systemDictionary.hpp
+++ b/hotspot/src/share/vm/classfile/systemDictionary.hpp
@@ -649,6 +649,7 @@ public:
Handle class_loader,
TRAPS);
static bool is_ext_class_loader(Handle class_loader);
+ static bool is_app_class_loader(Handle class_loader);
protected:
static Klass* find_shared_class(Symbol* class_name);
diff --git a/hotspot/src/share/vm/classfile/systemDictionaryShared.hpp b/hotspot/src/share/vm/classfile/systemDictionaryShared.hpp
index e1adf8b..a8dbda2 100644
--- a/hotspot/src/share/vm/classfile/systemDictionaryShared.hpp
+++ b/hotspot/src/share/vm/classfile/systemDictionaryShared.hpp
@@ -35,13 +35,25 @@ public:
static instanceKlassHandle find_or_load_shared_class(Symbol* class_name,
Handle class_loader,
TRAPS) {
+ if (UseAppCDS) {
+ instanceKlassHandle ik = load_shared_class(class_name, class_loader, CHECK_NULL);
+ if (!ik.is_null()) {
+ instanceKlassHandle nh = instanceKlassHandle(); // null Handle
+ ik = find_or_define_instance_class(class_name, class_loader, ik, CHECK_(nh));
+ }
+ return ik;
+ }
return instanceKlassHandle();
}
static void roots_oops_do(OopClosure* blk) {}
static void oops_do(OopClosure* f) {}
+
static bool is_sharing_possible(ClassLoaderData* loader_data) {
oop class_loader = loader_data->class_loader();
- return (class_loader == NULL);
+ return (class_loader == NULL ||
+ (UseAppCDS && (SystemDictionary::is_app_class_loader(class_loader) ||
+ SystemDictionary::is_ext_class_loader(class_loader)))
+ );
}
static size_t dictionary_entry_size() {
diff --git a/hotspot/src/share/vm/classfile/vmSymbols.hpp b/hotspot/src/share/vm/classfile/vmSymbols.hpp
index f72a948..6bd8dbe 100644
--- a/hotspot/src/share/vm/classfile/vmSymbols.hpp
+++ b/hotspot/src/share/vm/classfile/vmSymbols.hpp
@@ -418,8 +418,8 @@
template(getFileURL_signature, "(Ljava/io/File;)Ljava/net/URL;") \
template(definePackageInternal_name, "definePackageInternal") \
template(definePackageInternal_signature, "(Ljava/lang/String;Ljava/util/jar/Manifest;Ljava/net/URL;)V") \
- template(getProtectionDomain_name, "getProtectionDomain") \
- template(getProtectionDomain_signature, "(Ljava/security/CodeSource;)Ljava/security/ProtectionDomain;") \
+ template(getProtectionDomainInternal_name, "getProtectionDomainInternal") \
+ template(getProtectionDomainInternal_signature, "(Ljava/lang/String;)Ljava/security/ProtectionDomain;") \
template(url_code_signer_array_void_signature, "(Ljava/net/URL;[Ljava/security/CodeSigner;)V") \
template(resolved_references_name, "<resolved_references>") \
template(referencequeue_null_name, "NULL") \
diff --git a/hotspot/src/share/vm/memory/filemap.cpp b/hotspot/src/share/vm/memory/filemap.cpp
index 644e3b1..0f3c076 100644
--- a/hotspot/src/share/vm/memory/filemap.cpp
+++ b/hotspot/src/share/vm/memory/filemap.cpp
@@ -344,12 +344,12 @@ bool FileMapInfo::init_from_file(int fd) {
// Read the FileMapInfo information from the file.
bool FileMapInfo::open_for_read() {
- _full_path = Arguments::GetSharedArchivePath();
+ _full_path = make_log_name(Arguments::GetSharedArchivePath(), NULL);
int fd = open(_full_path, O_RDONLY | O_BINARY, 0);
if (fd < 0) {
if (errno == ENOENT) {
// Not locating the shared archive is ok.
- fail_continue("Specified shared archive not found.");
+ fail_continue("Specified shared archive not found. archive file path:%s", _full_path);
} else {
fail_continue("Failed to open shared archive file (%s).",
strerror(errno));
@@ -366,7 +366,7 @@ bool FileMapInfo::open_for_read() {
// Write the FileMapInfo information to the file.
void FileMapInfo::open_for_write() {
- _full_path = Arguments::GetSharedArchivePath();
+ _full_path = make_log_name(Arguments::GetSharedArchivePath(), NULL);
if (PrintSharedSpaces) {
tty->print_cr("Dumping shared data to file: ");
tty->print_cr(" %s", _full_path);
diff --git a/hotspot/src/share/vm/memory/metaspaceShared.cpp b/hotspot/src/share/vm/memory/metaspaceShared.cpp
index d5826d6..f3c3c51 100644
--- a/hotspot/src/share/vm/memory/metaspaceShared.cpp
+++ b/hotspot/src/share/vm/memory/metaspaceShared.cpp
@@ -677,14 +677,9 @@ void MetaspaceShared::link_and_cleanup_shared_classes(TRAPS) {
SystemDictionary::classes_do(check_one_shared_class);
} while (_check_classes_made_progress);
- if (IgnoreUnverifiableClassesDuringDump) {
- // This is useful when running JCK or SQE tests. You should not
- // enable this when running real apps.
- SystemDictionary::remove_classes_in_error_state();
- } else {
- tty->print_cr("Please remove the unverifiable classes from your class list and try again");
- exit(1);
- }
+ // record error message, remove error state, and continue to dump jsa file
+ tty->print_cr("Please remove the unverifiable classes from your class list and try again");
+ SystemDictionary::remove_classes_in_error_state();
}
// Copy the dependencies from C_HEAP-alloced GrowableArrays to RO-alloced
@@ -803,8 +798,12 @@ int MetaspaceShared::preload_and_dump(const char * class_list_path,
// Got a class name - load it.
TempNewSymbol class_name_symbol = SymbolTable::new_permanent_symbol(class_name, THREAD);
guarantee(!HAS_PENDING_EXCEPTION, "Exception creating a symbol.");
+
+ Handle loader = UseAppCDS ? SystemDictionary::java_system_loader() : Handle();
Klass* klass = SystemDictionary::resolve_or_null(class_name_symbol,
- THREAD);
+ loader,
+ Handle(),
+ THREAD);
CLEAR_PENDING_EXCEPTION;
if (klass != NULL) {
if (PrintSharedSpaces && Verbose && WizardMode) {
@@ -824,8 +823,8 @@ int MetaspaceShared::preload_and_dump(const char * class_list_path,
guarantee(!HAS_PENDING_EXCEPTION, "exception in link_class");
class_count++;
- } else {
- //tty->print_cr("Preload failed: %s", class_name);
+ } else if (UseAppCDS) {
+ tty->print_cr("Preload failed: %s", class_name);
}
}
fclose(file);
diff --git a/hotspot/src/share/vm/oops/arrayKlass.cpp b/hotspot/src/share/vm/oops/arrayKlass.cpp
index 2d2e44b..129bce6 100644
--- a/hotspot/src/share/vm/oops/arrayKlass.cpp
+++ b/hotspot/src/share/vm/oops/arrayKlass.cpp
@@ -195,6 +195,12 @@ void ArrayKlass::remove_unshareable_info() {
Klass::remove_unshareable_info();
// Clear the java mirror
set_component_mirror(NULL);
+
+ if (_higher_dimension != NULL) {
+ ArrayKlass *ak = ArrayKlass::cast(higher_dimension());
+ ak->remove_unshareable_info();
+ }
+ _higher_dimension = NULL;
}
void ArrayKlass::restore_unshareable_info(ClassLoaderData* loader_data, Handle protection_domain, TRAPS) {
diff --git a/hotspot/src/share/vm/oops/constantPool.cpp b/hotspot/src/share/vm/oops/constantPool.cpp
index 98a11fe..4502a01 100644
--- a/hotspot/src/share/vm/oops/constantPool.cpp
+++ b/hotspot/src/share/vm/oops/constantPool.cpp
@@ -180,6 +180,20 @@ void ConstantPool::restore_unshareable_info(TRAPS) {
}
void ConstantPool::remove_unshareable_info() {
+ if (UseAppCDS) {
+ if (cache() != NULL) {
+ cache()->reset();
+ }
+ for (int i = 0; i < _length; i++) {
+ if (tag_at(i).is_klass()) {
+ Klass* resolvedKlass = resolved_klass_at(i);
+ ResourceMark rm;
+ char* name = resolvedKlass->name()->as_C_string();
+ int len = strlen(name);
+ unresolved_klass_at_put(i, resolvedKlass->name());
+ }
+ }
+ }
// Resolved references are not in the shared archive.
// Save the length for restoration. It is not necessarily the same length
// as reference_map.length() if invokedynamic is saved.
diff --git a/hotspot/src/share/vm/oops/cpCache.cpp b/hotspot/src/share/vm/oops/cpCache.cpp
index cda9a4e..ebcf3d6 100644
--- a/hotspot/src/share/vm/oops/cpCache.cpp
+++ b/hotspot/src/share/vm/oops/cpCache.cpp
@@ -673,3 +673,16 @@ void ConstantPoolCache::verify_on(outputStream* st) {
// print constant pool cache entries
for (int i = 0; i < length(); i++) entry_at(i)->verify(st);
}
+
+void ConstantPoolCache::reset() {
+ for (int i = 0; i < length(); i++) {
+ ConstantPoolCacheEntry* entry = entry_at(i);
+ int cp_index = entry->constant_pool_index();
+ if (!entry->is_initial_resolved_ref_index()) {
+ // constant pool cache after initialization contains
+ // placeholders fr handling invokedynamic and invokehandle -
+ // these need to be preserved and all other entries reset
+ entry->initialize_entry(cp_index);
+ }
+ }
+}
diff --git a/hotspot/src/share/vm/oops/cpCache.hpp b/hotspot/src/share/vm/oops/cpCache.hpp
index a4a6c3f..48f9bbd 100644
--- a/hotspot/src/share/vm/oops/cpCache.hpp
+++ b/hotspot/src/share/vm/oops/cpCache.hpp
@@ -360,7 +360,14 @@ class ConstantPoolCacheEntry VALUE_OBJ_CLASS_SPEC {
bool is_double() const { return flag_state() == dtos; }
TosState flag_state() const { assert((uint)number_of_states <= (uint)tos_state_mask+1, "");
return (TosState)((_flags >> tos_state_shift) & tos_state_mask); }
-
+ bool is_initial_resolved_ref_index() const {
+ if (_flags == 0 && _f1 == NULL && bytecode_1() == Bytecodes::_nop && bytecode_2() == Bytecodes::_nop) {
+ return true;
+ } else {
+ return false;
+ }
+ }
+
// Code generation support
static WordSize size() { return in_WordSize(sizeof(ConstantPoolCacheEntry) / HeapWordSize); }
static ByteSize size_in_bytes() { return in_ByteSize(sizeof(ConstantPoolCacheEntry)); }
@@ -480,6 +487,8 @@ class ConstantPoolCache: public MetaspaceObj {
void dump_cache();
#endif // INCLUDE_JVMTI
+ void reset();
+
// Deallocate - no fields to deallocate
DEBUG_ONLY(bool on_stack() { return false; })
void deallocate_contents(ClassLoaderData* data) {}
diff --git a/hotspot/src/share/vm/oops/instanceKlass.cpp b/hotspot/src/share/vm/oops/instanceKlass.cpp
index 6f881ac..6d67113 100644
--- a/hotspot/src/share/vm/oops/instanceKlass.cpp
+++ b/hotspot/src/share/vm/oops/instanceKlass.cpp
@@ -2452,6 +2452,22 @@ void InstanceKlass::remove_unshareable_info() {
m->remove_unshareable_info();
}
+ if (UseAppCDS) {
+ if (_oop_map_cache != NULL) {
+ delete _oop_map_cache;
+ _oop_map_cache = NULL;
+ }
+
+ JNIid::deallocate(jni_ids());
+ set_jni_ids(NULL);
+
+ jmethodID* jmeths = methods_jmethod_ids_acquire();
+ if (jmeths != (jmethodID*)NULL) {
+ release_set_methods_jmethod_ids(NULL);
+ FreeHeap(jmeths);
+ }
+ }
+
// do array classes also.
array_klasses_do(remove_unshareable_in_class);
}
diff --git a/hotspot/src/share/vm/oops/klass.cpp b/hotspot/src/share/vm/oops/klass.cpp
index ba20471..399290f 100644
--- a/hotspot/src/share/vm/oops/klass.cpp
+++ b/hotspot/src/share/vm/oops/klass.cpp
@@ -63,6 +63,9 @@ void Klass::set_is_cloneable() {
}
}
+ClassLoaderData *Klass::_fake_loader_data_App = reinterpret_cast<ClassLoaderData *>(0xFDFDFDFA);
+ClassLoaderData *Klass::_fake_loader_data_Ext = reinterpret_cast<ClassLoaderData *>(0xFDFDFDFB);
+
void Klass::set_name(Symbol* n) {
_name = n;
if (_name != NULL) _name->increment_refcount();
@@ -536,8 +539,21 @@ void Klass::remove_unshareable_info() {
set_java_mirror(NULL);
set_next_link(NULL);
- // Null out class_loader_data because we don't share that yet.
- set_class_loader_data(NULL);
+ if (!UseAppCDS) {
+ // CDS logic
+ set_class_loader_data(NULL);
+ } else if (class_loader_data() != NULL) {
+ // AppCDS logic
+ if (class_loader() == NULL) {
+ // Null out class loader data for classes loaded by bootstrap (null) loader
+ set_class_loader_data(NULL);
+ } else if(SystemDictionary::is_ext_class_loader(class_loader())) {
+ // Mark class loaded by system class loader
+ set_class_loader_data(_fake_loader_data_Ext);
+ } else {
+ set_class_loader_data(_fake_loader_data_App);
+ }
+ }
}
void Klass::restore_unshareable_info(ClassLoaderData* loader_data, Handle protection_domain, TRAPS) {
@@ -545,7 +561,10 @@ void Klass::restore_unshareable_info(ClassLoaderData* loader_data, Handle protec
// If an exception happened during CDS restore, some of these fields may already be
// set. We leave the class on the CLD list, even if incomplete so that we don't
// modify the CLD list outside a safepoint.
- if (class_loader_data() == NULL) {
+ if (class_loader_data() == NULL || has_fake_loader_data()) {
+ // CDS should not set fake loader data
+ assert(!has_fake_loader_data() || (has_fake_loader_data() && UseAppCDS),
+ "setting fake loader data possible only with AppCDS enabled");
// Restore class_loader_data
set_class_loader_data(loader_data);
diff --git a/hotspot/src/share/vm/oops/klass.hpp b/hotspot/src/share/vm/oops/klass.hpp
index 428df42..cb7640c 100644
--- a/hotspot/src/share/vm/oops/klass.hpp
+++ b/hotspot/src/share/vm/oops/klass.hpp
@@ -188,6 +188,10 @@ private:
// -1.
jshort _shared_class_path_index;
+ // This is used only during AppCDS to mark classes that have non-null class loader
+ static ClassLoaderData* _fake_loader_data_App;
+ static ClassLoaderData* _fake_loader_data_Ext;
+
friend class SharedClassUtil;
protected:
@@ -202,6 +206,10 @@ protected:
enum StaticLookupMode { find_static, skip_static };
enum PrivateLookupMode { find_private, skip_private };
+ bool has_fake_loader_data_App() { return class_loader_data() == _fake_loader_data_App; }
+ bool has_fake_loader_data_Ext() { return class_loader_data() == _fake_loader_data_Ext; }
+ bool has_fake_loader_data() { return (has_fake_loader_data_App() || has_fake_loader_data_Ext()); }
+
bool is_klass() const volatile { return true; }
// super
diff --git a/hotspot/src/share/vm/runtime/arguments.cpp b/hotspot/src/share/vm/runtime/arguments.cpp
index f9b6bd3..a04dcac 100644
--- a/hotspot/src/share/vm/runtime/arguments.cpp
+++ b/hotspot/src/share/vm/runtime/arguments.cpp
@@ -3020,6 +3020,23 @@ jint Arguments::parse_each_vm_init_arg(const JavaVMInitArgs* args,
// Remaining part of option string
const char* tail;
+ // Special handling for UseAppCDS flag - it has to enable
+ // SharedArviveFile flag no matter where it's located in the
+ // argument list (and in order to enable UseAppCDS)
+ for (int index = 0; index < args->nOptions; index++) {
+ const JavaVMOption* option = args->options + index;
+ if (match_option(option, "-XX:+UseAppCDS", &tail)) {
+ if (!process_argument("+UseAppCDS", args->ignoreUnrecognized, origin)) {
+ return JNI_EINVAL;
+ } else {
+ const char* n = "SharedArchiveFile";
+ Flag* shared_archive_flag = Flag::find_flag(n, strlen(n), true, true);
+ shared_archive_flag->unlock_diagnostic();
+ FLAG_SET_CMDLINE(bool, UseAppCDS, true);
+ }
+ }
+ }
+
// iterate over arguments
for (int index = 0; index < args->nOptions; index++) {
bool is_absolute_path = false; // for -agentpath vs -agentlib
diff --git a/hotspot/src/share/vm/runtime/globals.hpp b/hotspot/src/share/vm/runtime/globals.hpp
index 46bbfb4..520cc31 100644
--- a/hotspot/src/share/vm/runtime/globals.hpp
+++ b/hotspot/src/share/vm/runtime/globals.hpp
@@ -4010,6 +4010,9 @@ class CommandLineFlags {
product(ccstr, ExtraSharedClassListFile, NULL, \
"Extra classlist for building the CDS archive file") \
\
+ product(bool, UseAppCDS, false, \
+ "Enable Application Class Data Sharing (AppCDS)") \
+ \
experimental(uintx, ArrayAllocatorMallocLimit, \
SOLARIS_ONLY(64*K) NOT_SOLARIS(max_uintx), \
"Allocation less than this value will be allocated " \
diff --git a/hotspot/src/share/vm/runtime/javaCalls.cpp b/hotspot/src/share/vm/runtime/javaCalls.cpp
index 12925a9..217b8ff 100644
--- a/hotspot/src/share/vm/runtime/javaCalls.cpp
+++ b/hotspot/src/share/vm/runtime/javaCalls.cpp
@@ -310,7 +310,7 @@ void JavaCalls::call(JavaValue* result, methodHandle method, JavaCallArguments*
void JavaCalls::call_helper(JavaValue* result, methodHandle* m, JavaCallArguments* args, TRAPS) {
// During dumping, Java execution environment is not fully initialized. Also, Java execution
// may cause undesirable side-effects in the class metadata.
- assert(!DumpSharedSpaces, "must not execute Java bytecodes when dumping");
+ assert(!DumpSharedSpaces || UseAppCDS, "must not execute Java bytecodes when dumping");
methodHandle method = *m;
JavaThread* thread = (JavaThread*)THREAD;
diff --git a/hotspot/src/share/vm/runtime/thread.cpp b/hotspot/src/share/vm/runtime/thread.cpp
index 03b6aaf..03c1098 100644
--- a/hotspot/src/share/vm/runtime/thread.cpp
+++ b/hotspot/src/share/vm/runtime/thread.cpp
@@ -3428,6 +3428,14 @@ jint Threads::create_vm(JavaVMInitArgs* args, bool* canTryAgain) {
os::pause();
}
+ if (DumpSharedSpaces) {
+ // when dumping shared spaces for AppCDS we must disable bytecode
+ // rewriting as it initializes internal (cached) meta-data that
+ // would be stored in the archive but cannot be carried over to
+ // the next execution
+ RewriteBytecodes = false;
+ }
+
#ifndef USDT2
HS_DTRACE_PROBE(hotspot, vm__init__begin);
#else /* USDT2 */
@@ -3554,8 +3562,8 @@ jint Threads::create_vm(JavaVMInitArgs* args, bool* canTryAgain) {
// At this point, the Universe is initialized, but we have not executed
// any byte code. Now is a good time (the only time) to dump out the
- // internal state of the JVM for sharing.
- if (DumpSharedSpaces) {
+ // internal state of the JVM for sharing, unless AppCDS is enabled.
+ if (!UseAppCDS && DumpSharedSpaces) {
MetaspaceShared::preload_and_dump(CHECK_0);
ShouldNotReachHere();
}
@@ -3682,6 +3690,11 @@ jint Threads::create_vm(JavaVMInitArgs* args, bool* canTryAgain) {
vm_exit_during_initialization(Handle(THREAD, PENDING_EXCEPTION));
}
+ if (UseAppCDS && DumpSharedSpaces) {
+ MetaspaceShared::preload_and_dump(CHECK_0);
+ ShouldNotReachHere();
+ }
+
#if INCLUDE_ALL_GCS
// Support for ConcurrentMarkSweep. This should be cleaned up
// and better encapsulated. The ugly nested if test would go away
diff --git a/hotspot/src/share/vm/utilities/ostream.cpp b/hotspot/src/share/vm/utilities/ostream.cpp
index fc17aeb..2b458fe 100644
--- a/hotspot/src/share/vm/utilities/ostream.cpp
+++ b/hotspot/src/share/vm/utilities/ostream.cpp
@@ -495,7 +495,7 @@ static const char* make_log_name_internal(const char* log_name, const char* forc
// -XX:DumpLoadedClassList=<file_name>
// in log_name, %p => pid1234 and
// %t => YYYY-MM-DD_HH-MM-SS
-static const char* make_log_name(const char* log_name, const char* force_directory) {
+const char* make_log_name(const char* log_name, const char* force_directory) {
char timestr[32];
get_datetime_string(timestr, sizeof(timestr));
return make_log_name_internal(log_name, force_directory, os::current_process_id(),
diff --git a/hotspot/src/share/vm/utilities/ostream.hpp b/hotspot/src/share/vm/utilities/ostream.hpp
index fbcb299..530c523 100644
--- a/hotspot/src/share/vm/utilities/ostream.hpp
+++ b/hotspot/src/share/vm/utilities/ostream.hpp
@@ -332,4 +332,6 @@ class networkStream : public bufferedStream {
#endif
+const char* make_log_name(const char* log_name, const char* force_directory);
+
#endif // SHARE_VM_UTILITIES_OSTREAM_HPP
diff --git a/jdk/src/share/classes/java/lang/ClassLoader.java b/jdk/src/share/classes/java/lang/ClassLoader.java
index 2e98092..f305c1e 100644
--- a/jdk/src/share/classes/java/lang/ClassLoader.java
+++ b/jdk/src/share/classes/java/lang/ClassLoader.java
@@ -2182,6 +2182,10 @@ public abstract class ClassLoader {
// Retrieves the assertion directives from the VM.
private static native AssertionStatusDirectives retrieveDirectives();
+
+ protected ProtectionDomain getProtectionDomainInternal(String name) {
+ return null;
+ }
}
diff --git a/jdk/src/share/classes/java/net/URLClassLoader.java b/jdk/src/share/classes/java/net/URLClassLoader.java
index 416941c..e82cb6d 100644
--- a/jdk/src/share/classes/java/net/URLClassLoader.java
+++ b/jdk/src/share/classes/java/net/URLClassLoader.java
@@ -38,6 +38,7 @@ import java.security.Permission;
import java.security.PermissionCollection;
import java.security.PrivilegedAction;
import java.security.PrivilegedExceptionAction;
+import java.security.ProtectionDomain;
import java.security.SecureClassLoader;
import java.util.Enumeration;
import java.util.List;
@@ -343,6 +344,25 @@ public class URLClassLoader extends SecureClassLoader implements Closeable {
return ucp.getURLs();
}
+ /*
+ * Retrieve protection domain using the specified class name.
+ * Called from the VM to support AppCDS
+ */
+ protected ProtectionDomain getProtectionDomainInternal(String name) {
+ String path = name.replace('.', '/').concat(".class");
+ Resource res = ucp.getResource(path, false);
+
+ if(res == null)
+ {
+ // Should never happen
+ throw new AssertionError("Cannot find resource fpr path " + path);
+ }
+ URL url = res.getCodeSourceURL();
+ CodeSigner[] signers = res.getCodeSigners();
+ CodeSource cs = new CodeSource(url, signers);
+ return getProtectionDomain(cs);
+ }
+
/**
* Finds and loads the class with the specified name from the URL search
* path. Any URLs referring to JAR files are loaded and opened as needed
diff --git a/jdk/src/share/classes/java/security/SecureClassLoader.java b/jdk/src/share/classes/java/security/SecureClassLoader.java
index 145f4fc..cb5f017 100644
--- a/jdk/src/share/classes/java/security/SecureClassLoader.java
+++ b/jdk/src/share/classes/java/security/SecureClassLoader.java
@@ -195,7 +195,7 @@ public class SecureClassLoader extends ClassLoader {
/*
* Returned cached ProtectionDomain for the specified CodeSource.
*/
- private ProtectionDomain getProtectionDomain(CodeSource cs) {
+ protected ProtectionDomain getProtectionDomain(CodeSource cs) {
if (cs == null)
return null;
@@ -215,6 +215,7 @@ public class SecureClassLoader extends ClassLoader {
return pd;
}
+
/*
* Check to make sure the class loader has been initialized.
*/

View File

@ -0,0 +1,27 @@
From a409bdd4982a6a463b65b529ed3aedb0c3e29144 Mon Sep 17 00:00:00 2001
Date: Mon, 17 Aug 2020 19:32:33 +0000
Subject: [PATCH] Fix LineBuffer::vappend when buffer too small
Summary: <runtime>: fix LineBuffer::vappend when buffer too small
LLT: NA
Bug url: NA
---
hotspot/src/share/vm/gc_implementation/g1/g1GCPhaseTimes.cpp | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/hotspot/src/share/vm/gc_implementation/g1/g1GCPhaseTimes.cpp b/hotspot/src/share/vm/gc_implementation/g1/g1GCPhaseTimes.cpp
index 75a9a5f95..185b7d67e 100644
--- a/hotspot/src/share/vm/gc_implementation/g1/g1GCPhaseTimes.cpp
+++ b/hotspot/src/share/vm/gc_implementation/g1/g1GCPhaseTimes.cpp
@@ -42,7 +42,7 @@ private:
void vappend(const char* format, va_list ap) ATTRIBUTE_PRINTF(2, 0) {
int res = os::vsnprintf(&_buffer[_cur], BUFFER_LEN - _cur, format, ap);
- if (res > BUFFER_LEN) {
+ if (_cur + res > BUFFER_LEN) {
DEBUG_ONLY(warning("buffer too small in LineBuffer");)
_buffer[BUFFER_LEN -1] = 0;
_cur = BUFFER_LEN; // vsnprintf above should not add to _buffer if we are called again
--
2.12.3

View File

@ -0,0 +1,51 @@
From bd4fd0ac21f668f9f91e802e73cad0c120ba9df6 Mon Sep 17 00:00:00 2001
Date: Thu, 4 Jun 2020 15:45:47 +0800
Subject: [PATCH] Remove unused GenericTaskQueueSet<T, F>::tasks()
Summary: <gc>: remove unused GenericTaskQueueSet<T, F>::tasks()
LLT: NA
Bug url: NA
---
hotspot/src/share/vm/utilities/taskqueue.hpp | 12 ------------
1 file changed, 12 deletions(-)
diff --git a/hotspot/src/share/vm/utilities/taskqueue.hpp b/hotspot/src/share/vm/utilities/taskqueue.hpp
index 5b03ccfa..9a2e2ee2 100644
--- a/hotspot/src/share/vm/utilities/taskqueue.hpp
+++ b/hotspot/src/share/vm/utilities/taskqueue.hpp
@@ -541,8 +541,6 @@ class TaskQueueSetSuper {
public:
// Returns "true" if some TaskQueue in the set contains a task.
virtual bool peek() = 0;
- // Tasks in queue
- virtual uint tasks() const = 0;
virtual size_t tasks() = 0;
};
@@ -576,7 +574,6 @@ public:
// Returns if stealing succeeds, and sets "t" to the stolen task.
bool steal(uint queue_num, E& t);
bool peek();
- uint tasks() const;
size_t tasks();
uint size() const { return _n; }
@@ -675,15 +672,6 @@ size_t GenericTaskQueueSet<T, F>::tasks() {
return n;
}
-template<class T, MEMFLAGS F>
-uint GenericTaskQueueSet<T, F>::tasks() const {
- uint n = 0;
- for (uint j = 0; j < _n; j++) {
- n += _queues[j]->size();
- }
- return n;
-}
-
// When to terminate from the termination protocol.
class TerminatorTerminator: public CHeapObj<mtInternal> {
public:
--
2.19.0

View File

@ -0,0 +1,68 @@
From 9945034658585ea943e6326340c06b5932af8d67 Mon Sep 17 00:00:00 2001
Date: Thu, 5 Dec 2019 10:29:18 +0000
Subject: [PATCH] Support 'Git commit ID' in the SOURCE field of the release
file.
Summary: <make>:Support 'Git commit ID' in the SOURCE field of the release file.
LLT: NA
Bug url: NA
---
common/autoconf/spec.gmk.in | 1 +
make/common/MakeBase.gmk | 29 +++++++++++++++++------------
2 files changed, 18 insertions(+), 12 deletions(-)
diff --git a/common/autoconf/spec.gmk.in b/common/autoconf/spec.gmk.in
index 88f9f539..506cf617 100644
--- a/common/autoconf/spec.gmk.in
+++ b/common/autoconf/spec.gmk.in
@@ -578,6 +578,7 @@ READELF:=@READELF@
EXPR:=@EXPR@
FILE:=@FILE@
HG:=@HG@
+GIT:=@GIT@
OBJCOPY:=@OBJCOPY@
SETFILE:=@SETFILE@
XATTR:=@XATTR@
diff --git a/make/common/MakeBase.gmk b/make/common/MakeBase.gmk
index 9e5e704b..9b7ad702 100644
--- a/make/common/MakeBase.gmk
+++ b/make/common/MakeBase.gmk
@@ -308,18 +308,23 @@ REPO_LIST = $(patsubst ./%,%,$(patsubst %/,%,$(sort $(dir \
# Emit the repo:id pairs to $@
define GetSourceTips
- $(CD) $(SRC_ROOT) ; \
- for i in $(REPO_LIST) IGNORE ; do \
- if [ "$${i}" = "IGNORE" ] ; then \
- continue; \
- elif [ -d $${i}/$(HG_DIRECTORY) -a "$(HG_VERSION)" != "" ] ; then \
- $(PRINTF) " %s:%s" \
- "$${i}" `$(HG) id -i --repository $${i}` ; \
- elif [ -f $${i}/$(HGTIP_FILENAME) ] ; then \
- $(PRINTF) " %s:%s" \
- "$${i}" `$(CAT) $${i}/$(HGTIP_FILENAME)` ; \
- fi; \
- done >> $@
+ $(if $(and $(HG), $(wildcard $(TOPDIR)/.hg)), \
+ $$($(CD) $(SRC_ROOT) ; \
+ for i in $(REPO_LIST) IGNORE ; do \
+ if [ "$${i}" = "IGNORE" ] ; then \
+ continue; \
+ elif [ -d $${i}/$(HG_DIRECTORY) -a "$(HG_VERSION)" != "" ] ; then \
+ $(PRINTF) " %s:%s" \
+ "$${i}" `$(HG) id -i --repository $${i}` ; \
+ elif [ -f $${i}/$(HGTIP_FILENAME) ] ; then \
+ $(PRINTF) " %s:%s" \
+ "$${i}" `$(CAT) $${i}/$(HGTIP_FILENAME)` ; \
+ fi; \
+ done >> $@), \
+ $(if $(and $(GIT), $(wildcard $(TOPDIR)/.git)), \
+ $(PRINTF) ".:git:%s%s\n" \
+ "$$(git log -n1 --format=%H | cut -c1-12)" \
+ "$$(if test -n "$$(git status --porcelain)"; then printf '+'; fi)" >> $@, ))
$(PRINTF) "\n" >> $@
endef
--
2.19.0

View File

@ -0,0 +1,37 @@
From 0cf95d445b1f6854249987ec55591e26cc21c6a1 Mon Sep 17 00:00:00 2001
Date: Thu, 14 May 2020 09:59:34 +0800
Subject: [PATCH] Test8167409.sh fails to run with 32bit jdk on 64bit system
Summary: <test case>: Test8167409.sh fails to run with 32bit jdk on 64bit system
LLT: jdk8u/hotspot/test/compiler/criticalnatives/argumentcorruption/Test8167409.sh
Bug url:
---
.../criticalnatives/argumentcorruption/Test8167409.sh | 6 +++++-
1 file changed, 5 insertions(+), 1 deletion(-)
diff --git a/hotspot/test/compiler/criticalnatives/argumentcorruption/Test8167409.sh b/hotspot/test/compiler/criticalnatives/argumentcorruption/Test8167409.sh
index 81695e75..1108aaf9 100644
--- a/hotspot/test/compiler/criticalnatives/argumentcorruption/Test8167409.sh
+++ b/hotspot/test/compiler/criticalnatives/argumentcorruption/Test8167409.sh
@@ -61,13 +61,17 @@ case "$OS" in
exit 0;
;;
esac
+${TESTJAVA}${FS}bin${FS}java -XshowSettings 2>&1 | grep sun.arch.data.model | grep 32
+if [ 0 -eq $? ] ; then
+ M32="-m32"
+fi
THIS_DIR=.
cp ${TESTSRC}${FS}*.java ${THIS_DIR}
${TESTJAVA}${FS}bin${FS}javac *.java
-$cc_cmd -fPIC -shared -o libCNCheckLongArgs.so \
+$cc_cmd ${M32} -fPIC -shared -o libCNCheckLongArgs.so \
-I${TESTJAVA}${FS}include -I${TESTJAVA}${FS}include${FS}linux \
${TESTSRC}${FS}libCNCheckLongArgs.c
--
2.19.0

View File

@ -0,0 +1,27 @@
From 952b5418911a0cbe864d83998b1c99904830d463 Mon Sep 17 00:00:00 2001
Date: Fri, 28 Aug 2020 09:21:14 +0800
Subject: [PATCH] The runok method retrying another port does not take effect
Summary: <java.rmi>: The runok method retrying another port does not take effect
LLT: jdk8u/jdk/test/sun/management/jmxremote/bootstrap/RmiBootstrapTest.sh
Bug url:
---
jdk/test/sun/management/jmxremote/bootstrap/RmiBootstrapTest.java | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/jdk/test/sun/management/jmxremote/bootstrap/RmiBootstrapTest.java b/jdk/test/sun/management/jmxremote/bootstrap/RmiBootstrapTest.java
index d9c20c678..60219e68a 100644
--- a/jdk/test/sun/management/jmxremote/bootstrap/RmiBootstrapTest.java
+++ b/jdk/test/sun/management/jmxremote/bootstrap/RmiBootstrapTest.java
@@ -824,7 +824,7 @@ public class RmiBootstrapTest {
String errStr = null;
for (int i=0;i<conf.length;i++) {
- for (int j = 0; j < PORT_TEST_LEN; i++) {
+ for (int j = 0; j < PORT_TEST_LEN; j++) {
try {
errStr = testConfiguration(conf[i],port+testPort++);
break;
--
2.12.3

View File

@ -0,0 +1,25 @@
commit e1db4422be08222e4d5cf9fbfe8b8a61583976d2
Date: Tue Sep 15 20:58:00 2020 +0800
add DumpSharedSpace guarantee when create anonymous classes
Summary: < JDK> : add DumpSharedSpace guarantee when create anonymous classes
LLT: NA
Bug url: NA
diff --git a/hotspot/src/share/vm/prims/unsafe.cpp b/hotspot/src/share/vm/prims/unsafe.cpp
index f20bf3d2b..3ab82c5c4 100644
--- a/hotspot/src/share/vm/prims/unsafe.cpp
+++ b/hotspot/src/share/vm/prims/unsafe.cpp
@@ -1058,6 +1058,11 @@ Unsafe_DefineAnonymousClass_impl(JNIEnv *env,
HeapWord* *temp_alloc,
TRAPS) {
+ if (DumpSharedSpaces) {
+ tty->print_cr("failed: must not create anonymous classes when dumping.");
+ JVM_Exit(0);
+ }
+
if (UsePerfData) {
ClassLoader::unsafe_defineClassCallCounter()->inc();
}

View File

@ -1,12 +1,9 @@
From b5c192bb3dc57021996545b0bac822d73c75ec19 Mon Sep 17 00:00:00 2001
From: sunjianye <sunjianye@huawei.com>
Date: Thu, 23 Apr 2020 16:12:34 +0800
Subject: [PATCH] add vm option BoxTypeCachedMax for Integer and Long cache
DTS/AR: AR.SR.IREQ02373832.002.001
Summary: < JDK> : add vm option BoxTypeCachedMax for Integer and Long cache
LLT: NA
Patch Type: huawei
Bug url: NA
---
hotspot/src/share/vm/opto/c2_globals.hpp | 3 ++

676
fast-serializer-jdk8.patch Normal file
View File

@ -0,0 +1,676 @@
commit 3ece3b6a87e4bf61a1f786c12d796012becce313
Date: Thu May 28 10:30:20 2020 +0800
Add FastSerializer
Summary:<core-libs>: Add FastSerializer
LLT: jtreg
Bug url: NA
diff --git a/hotspot/src/share/vm/prims/unsafe.cpp b/hotspot/src/share/vm/prims/unsafe.cpp
index cdb72c0d5..d50041635 100644
--- a/hotspot/src/share/vm/prims/unsafe.cpp
+++ b/hotspot/src/share/vm/prims/unsafe.cpp
@@ -1361,6 +1361,10 @@ UNSAFE_ENTRY(void, Unsafe_PrefetchWrite(JNIEnv* env, jclass ignored, jobject obj
Prefetch::write(addr, (intx)offset);
UNSAFE_END
+UNSAFE_ENTRY(jboolean, Unsafe_GetUseFastSerializer(JNIEnv *env, jobject unsafe)) {
+ return UseFastSerializer;
+}
+UNSAFE_END
/// JVM_RegisterUnsafeMethods
@@ -1447,7 +1451,8 @@ static JNINativeMethod methods_140[] = {
{CC "allocateInstance", CC "(" CLS ")" OBJ, FN_PTR(Unsafe_AllocateInstance)},
{CC "monitorEnter", CC "(" OBJ ")V", FN_PTR(Unsafe_MonitorEnter)},
{CC "monitorExit", CC "(" OBJ ")V", FN_PTR(Unsafe_MonitorExit)},
- {CC "throwException", CC "(" THR ")V", FN_PTR(Unsafe_ThrowException)}
+ {CC "throwException", CC "(" THR ")V", FN_PTR(Unsafe_ThrowException)},
+ {CC "getUseFastSerializer", CC "()Z", FN_PTR(Unsafe_GetUseFastSerializer)}
};
// These are the methods prior to the JSR 166 changes in 1.5.0
@@ -1493,8 +1498,8 @@ static JNINativeMethod methods_141[] = {
{CC "allocateInstance", CC "(" CLS ")" OBJ, FN_PTR(Unsafe_AllocateInstance)},
{CC "monitorEnter", CC "(" OBJ ")V", FN_PTR(Unsafe_MonitorEnter)},
{CC "monitorExit", CC "(" OBJ ")V", FN_PTR(Unsafe_MonitorExit)},
- {CC "throwException", CC "(" THR ")V", FN_PTR(Unsafe_ThrowException)}
-
+ {CC "throwException", CC "(" THR ")V", FN_PTR(Unsafe_ThrowException)},
+ {CC "getUseFastSerializer", CC "()Z", FN_PTR(Unsafe_GetUseFastSerializer)}
};
// These are the methods prior to the JSR 166 changes in 1.6.0
@@ -1548,7 +1553,8 @@ static JNINativeMethod methods_15[] = {
{CC "compareAndSwapInt", CC "(" OBJ "J""I""I"")Z", FN_PTR(Unsafe_CompareAndSwapInt)},
{CC "compareAndSwapLong", CC "(" OBJ "J""J""J"")Z", FN_PTR(Unsafe_CompareAndSwapLong)},
{CC "park", CC "(ZJ)V", FN_PTR(Unsafe_Park)},
- {CC "unpark", CC "(" OBJ ")V", FN_PTR(Unsafe_Unpark)}
+ {CC "unpark", CC "(" OBJ ")V", FN_PTR(Unsafe_Unpark)},
+ {CC "getUseFastSerializer", CC "()Z", FN_PTR(Unsafe_GetUseFastSerializer)}
};
@@ -1606,7 +1612,8 @@ static JNINativeMethod methods_16[] = {
{CC "putOrderedInt", CC "(" OBJ "JI)V", FN_PTR(Unsafe_SetOrderedInt)},
{CC "putOrderedLong", CC "(" OBJ "JJ)V", FN_PTR(Unsafe_SetOrderedLong)},
{CC "park", CC "(ZJ)V", FN_PTR(Unsafe_Park)},
- {CC "unpark", CC "(" OBJ ")V", FN_PTR(Unsafe_Unpark)}
+ {CC "unpark", CC "(" OBJ ")V", FN_PTR(Unsafe_Unpark)},
+ {CC "getUseFastSerializer", CC "()Z", FN_PTR(Unsafe_GetUseFastSerializer)}
};
// These are the methods for 1.8.0
@@ -1662,7 +1669,8 @@ static JNINativeMethod methods_18[] = {
{CC "putOrderedInt", CC "(" OBJ "JI)V", FN_PTR(Unsafe_SetOrderedInt)},
{CC "putOrderedLong", CC "(" OBJ "JJ)V", FN_PTR(Unsafe_SetOrderedLong)},
{CC "park", CC "(ZJ)V", FN_PTR(Unsafe_Park)},
- {CC "unpark", CC "(" OBJ ")V", FN_PTR(Unsafe_Unpark)}
+ {CC "unpark", CC "(" OBJ ")V", FN_PTR(Unsafe_Unpark)},
+ {CC "getUseFastSerializer", CC "()Z", FN_PTR(Unsafe_GetUseFastSerializer)}
};
JNINativeMethod loadavg_method[] = {
diff --git a/hotspot/src/share/vm/runtime/globals.hpp b/hotspot/src/share/vm/runtime/globals.hpp
index 2e6ff26ed..0a6ebfae1 100644
--- a/hotspot/src/share/vm/runtime/globals.hpp
+++ b/hotspot/src/share/vm/runtime/globals.hpp
@@ -553,6 +553,10 @@ class CommandLineFlags {
"Enable normal processing of flags relating to experimental " \
"features") \
\
+ experimental(bool, UseFastSerializer, false, \
+ "Cache-based serialization.It is extremely fast, but it can only" \
+ "be effective in certain scenarios.") \
+ \
product(bool, JavaMonitorsInStackTrace, true, \
"Print information about Java monitor locks when the stacks are" \
"dumped") \
diff --git a/jdk/src/share/classes/java/io/ObjectInputStream.java b/jdk/src/share/classes/java/io/ObjectInputStream.java
index 5d30f2a01..b67f01719 100644
--- a/jdk/src/share/classes/java/io/ObjectInputStream.java
+++ b/jdk/src/share/classes/java/io/ObjectInputStream.java
@@ -52,6 +52,7 @@ import sun.misc.JavaOISAccess;
import sun.util.logging.PlatformLogger;
import sun.security.action.GetBooleanAction;
import sun.security.action.GetIntegerAction;
+import sun.misc.Unsafe;
/**
* An ObjectInputStream deserializes primitive data and objects previously
@@ -284,6 +285,22 @@ public class ObjectInputStream
traceLogger = (filterLog != null &&
filterLog.isLoggable(PlatformLogger.Level.FINER)) ? filterLog : null;
}
+
+ /*
+ * Logger for FastSerializer.
+ * Setup the FastSerializer logger if it is set to FINE
+ * (Assuming it will not change).
+ */
+ private static final PlatformLogger fastSerLogger;
+ static {
+ if (printFastSerializer) {
+ PlatformLogger fastSerLog = PlatformLogger.getLogger("fastSerializer");
+ fastSerLogger = (fastSerLog != null &&
+ fastSerLog.isLoggable(PlatformLogger.Level.FINE)) ? fastSerLog : null;
+ } else {
+ fastSerLogger = null;
+ }
+ }
}
/** filter stream for handling block data conversion */
@@ -312,6 +329,9 @@ public class ObjectInputStream
/** if true, invoke resolveObject() */
private boolean enableResolve;
+ /** Used to get the commandline option: useFastSerializer */
+ private static final Unsafe UNSAFE = Unsafe.getUnsafe();
+
/**
* Context during upcalls to class-defined readObject methods; holds
* object currently being deserialized and descriptor for current class.
@@ -325,6 +345,33 @@ public class ObjectInputStream
*/
private ObjectInputFilter serialFilter;
+ /**
+ * value of "useFastSerializer" property
+ */
+ private static final boolean defaultFastSerializer = UNSAFE.getUseFastSerializer();
+
+ /**
+ * true or false for open FastSerilizer
+ * May be changed in readStreamHeader
+ */
+ private boolean useFastSerializer = defaultFastSerializer;
+
+ /**
+ * Value of "fastSerializerEscapeMode" property. It can be turned on
+ * when useFastSerializer is true.
+ */
+ private static final boolean fastSerializerEscapeMode = java.security.AccessController.doPrivileged(
+ new sun.security.action.GetBooleanAction(
+ "fastSerializerEscapeMode")).booleanValue();
+
+ /**
+ * value of "printFastSerializer" property,
+ * as true or false for printing FastSerializer logs.
+ */
+ private static final boolean printFastSerializer = java.security.AccessController.doPrivileged(
+ new sun.security.action.GetBooleanAction(
+ "printFastSerializer")).booleanValue();
+
/**
* Creates an ObjectInputStream that reads from the specified InputStream.
* A serialization stream header is read from the stream and verified.
@@ -396,6 +443,9 @@ public class ObjectInputStream
* transitively so that a complete equivalent graph of objects is
* reconstructed by readObject.
*
+ * The difference between fastSerialzation and default serialization is the
+ * descriptor serialization. The data serialization is same with each other.
+ *
* <p>The root object is completely restored when all of its fields and the
* objects it references are completely restored. At this point the object
* validation callbacks are executed in order based on their registered
@@ -670,11 +720,20 @@ public class ObjectInputStream
vlist.register(obj, prio);
}
+ /**
+ * Cache the class meta during serialization.
+ * Only used in FastSerilizer.
+ */
+ protected static ConcurrentHashMap<String,Class<?>> nameToClass = new ConcurrentHashMap<>();
+
/**
* Load the local class equivalent of the specified stream class
* description. Subclasses may implement this method to allow classes to
* be fetched from an alternate source.
*
+ * When fastSerializer is turned on, fields of desc will be null except
+ * name. When resolveClass is override, this may cause null pointer exception.
+ *
* <p>The corresponding method in <code>ObjectOutputStream</code> is
* <code>annotateClass</code>. This method will be invoked only once for
* each unique class in the stream. This method can be implemented by
@@ -715,16 +774,27 @@ public class ObjectInputStream
throws IOException, ClassNotFoundException
{
String name = desc.getName();
+ Class<?> cl = null;
+
+ if (useFastSerializer) {
+ cl = nameToClass.get(name);
+ if (cl != null) {
+ return cl;
+ }
+ }
try {
- return Class.forName(name, false, latestUserDefinedLoader());
+ cl = Class.forName(name, false, latestUserDefinedLoader());
} catch (ClassNotFoundException ex) {
- Class<?> cl = primClasses.get(name);
- if (cl != null) {
- return cl;
- } else {
+ cl = primClasses.get(name);
+ if (cl == null) {
throw ex;
}
}
+ if (useFastSerializer) {
+ nameToClass.put(name, cl);
+ }
+
+ return cl;
}
/**
@@ -894,9 +964,34 @@ public class ObjectInputStream
{
short s0 = bin.readShort();
short s1 = bin.readShort();
- if (s0 != STREAM_MAGIC || s1 != STREAM_VERSION) {
- throw new StreamCorruptedException(
- String.format("invalid stream header: %04X%04X", s0, s1));
+ if (useFastSerializer) {
+ if (s0 != STREAM_MAGIC_FAST || s1 != STREAM_VERSION) {
+
+ if (s0 != STREAM_MAGIC) {
+ throw new StreamCorruptedException(
+ String.format("invalid stream header: %04X%04X, and FastSerializer is activated", s0, s1));
+ }
+
+ if (!fastSerializerEscapeMode) {
+ throw new StreamCorruptedException(
+ String.format("invalid stream header: %04X%04X.Fast serialization does not support " +
+ "original serialized files", s0, s1));
+ }
+
+ // Escape to default serialization
+ useFastSerializer = false;
+ if (Logging.fastSerLogger != null) {
+ Logging.fastSerLogger.fine("[Deserialize]: Escape and disable FastSerializer");
+ }
+ }
+ } else if (s0 != STREAM_MAGIC || s1 != STREAM_VERSION) {
+ if (s0 == STREAM_MAGIC_FAST && s1 == STREAM_VERSION) {
+ throw new StreamCorruptedException(
+ String.format("invalid stream header: %04X%04X, and it is a FastSerializer stream", s0, s1));
+ } else {
+ throw new StreamCorruptedException(
+ String.format("invalid stream header: %04X%04X", s0, s1));
+ }
}
}
@@ -910,6 +1005,11 @@ public class ObjectInputStream
* this method reads class descriptors according to the format defined in
* the Object Serialization specification.
*
+ * In fastSerialize mode, the descriptor is obtained by lookup method. And
+ * the resolveClass method is called here to get the classmeta. Since the
+ * descriptor is obtained by lookup, the descriptor is same as localdesc.
+ * So we cann't distinguish the receiver desc and local desc.
+ *
* @return the class descriptor read
* @throws IOException If an I/O error has occurred.
* @throws ClassNotFoundException If the Class of a serialized object used
@@ -920,6 +1020,27 @@ public class ObjectInputStream
protected ObjectStreamClass readClassDescriptor()
throws IOException, ClassNotFoundException
{
+ // fastSerializer
+ if (useFastSerializer) {
+ String name = readUTF();
+ Class<?> cl = null;
+ ObjectStreamClass desc = new ObjectStreamClass(name);
+ try {
+ // In order to match this method, we add an annotateClass method in
+ // writeClassDescriptor.
+ cl = resolveClass(desc);
+ } catch (ClassNotFoundException ex) {
+ // resolveClass is just used to obtain Class which required by lookup method
+ // and it will be called again later, so we don't throw ClassNotFoundException here.
+ return desc;
+ }
+ if (cl != null) {
+ desc = ObjectStreamClass.lookup(cl, true);
+ }
+ return desc;
+ }
+
+ // Default deserialization. If the Class cannot be found, throw ClassNotFoundException.
ObjectStreamClass desc = new ObjectStreamClass();
desc.readNonProxy(this);
return desc;
@@ -1935,17 +2056,40 @@ public class ObjectInputStream
skipCustomData();
- try {
- totalObjectRefs++;
- depth++;
- desc.initNonProxy(readDesc, cl, resolveEx, readClassDesc(false));
- } finally {
- depth--;
+ totalObjectRefs++;
+ depth++;
+
+ if (useFastSerializer) {
+ desc.initNonProxyFast(readDesc, resolveEx);
+ ObjectStreamClass superDesc = desc.getSuperDesc();
+ long originDepth = depth - 1;
+ // Since desc is obtained from the lookup method, we will lose the depth and
+ // totalObjectRefs of superDesc. So we add a loop here to compute the depth
+ // and objectRef of superDesc.
+ while (superDesc != null && superDesc.forClass() != null) {
+ filterCheck(superDesc.forClass(), -1);
+ superDesc = superDesc.getSuperDesc();
+ totalObjectRefs++;
+ depth++;
+ }
+ depth = originDepth;
+ } else {
+ try {
+ desc.initNonProxy(readDesc, cl, resolveEx, readClassDesc(false));
+ } finally {
+ depth--;
+ }
}
handles.finish(descHandle);
passHandle = descHandle;
+ if (Logging.fastSerLogger != null) {
+ Logging.fastSerLogger.fine(
+ "[Deserialize] useFastSerializer:{0}, Class name:{1}, SerialVersionUID:{2}, flags:{3}",
+ useFastSerializer, desc.getName(), desc.getSerialVersionUID(), desc.getFlags(this));
+ }
+
return desc;
}
@@ -2334,21 +2478,25 @@ public class ObjectInputStream
desc.setPrimFieldValues(obj, primVals);
}
- int objHandle = passHandle;
- ObjectStreamField[] fields = desc.getFields(false);
- Object[] objVals = new Object[desc.getNumObjFields()];
- int numPrimFields = fields.length - objVals.length;
- for (int i = 0; i < objVals.length; i++) {
- ObjectStreamField f = fields[numPrimFields + i];
- objVals[i] = readObject0(Object.class, f.isUnshared());
- if (f.getField() != null) {
- handles.markDependency(objHandle, passHandle);
+ Object[] objVals = null;
+ int numObjFields = desc.getNumObjFields();
+ if (numObjFields > 0) {
+ int objHandle = passHandle;
+ ObjectStreamField[] fields = desc.getFields(false);
+ objVals = new Object[numObjFields];
+ int numPrimFields = fields.length - objVals.length;
+ for (int i = 0; i < objVals.length; i++) {
+ ObjectStreamField f = fields[numPrimFields + i];
+ objVals[i] = readObject0(Object.class, f.isUnshared());
+ if (f.getField() != null) {
+ handles.markDependency(objHandle, passHandle);
+ }
}
+ if (obj != null) {
+ desc.setObjFieldValues(obj, objVals);
+ }
+ passHandle = objHandle;
}
- if (obj != null) {
- desc.setObjFieldValues(obj, objVals);
- }
- passHandle = objHandle;
}
/**
diff --git a/jdk/src/share/classes/java/io/ObjectOutputStream.java b/jdk/src/share/classes/java/io/ObjectOutputStream.java
index 6d29e3a1f..3890efc3e 100644
--- a/jdk/src/share/classes/java/io/ObjectOutputStream.java
+++ b/jdk/src/share/classes/java/io/ObjectOutputStream.java
@@ -37,6 +37,8 @@ import java.util.concurrent.ConcurrentMap;
import static java.io.ObjectStreamClass.processQueue;
import java.io.SerialCallbackContext;
import sun.reflect.misc.ReflectUtil;
+import sun.misc.Unsafe;
+import sun.util.logging.PlatformLogger;
/**
* An ObjectOutputStream writes primitive data types and graphs of Java objects
@@ -173,6 +175,24 @@ public class ObjectOutputStream
new ReferenceQueue<>();
}
+ private static class Logging {
+ /*
+ * Logger for FastSerializer.
+ * Setup the FastSerializer logger if it is set to FINE.
+ * (Assuming it will not change).
+ */
+ static final PlatformLogger fastSerLogger;
+ static {
+ if (printFastSerializer) {
+ PlatformLogger fastSerLog = PlatformLogger.getLogger("fastSerializer");
+ fastSerLogger = (fastSerLog != null &&
+ fastSerLog.isLoggable(PlatformLogger.Level.FINE)) ? fastSerLog : null;
+ } else {
+ fastSerLogger = null;
+ }
+ }
+ }
+
/** filter stream for handling block data conversion */
private final BlockDataOutputStream bout;
/** obj -> wire handle map */
@@ -214,6 +234,22 @@ public class ObjectOutputStream
new sun.security.action.GetBooleanAction(
"sun.io.serialization.extendedDebugInfo")).booleanValue();
+ private static final Unsafe UNSAFE = Unsafe.getUnsafe();
+
+ /**
+ * Value of "UseFastSerializer" property. The fastSerializer is turned
+ * on when it is true.
+ */
+ private static final boolean useFastSerializer = UNSAFE.getUseFastSerializer();
+
+ /**
+ * value of "printFastSerializer" property,
+ * as true or false for printing FastSerializer logs.
+ */
+ private static final boolean printFastSerializer = java.security.AccessController.doPrivileged(
+ new sun.security.action.GetBooleanAction(
+ "printFastSerializer")).booleanValue();
+
/**
* Creates an ObjectOutputStream that writes to the specified OutputStream.
* This constructor writes the serialization stream header to the
@@ -327,6 +363,9 @@ public class ObjectOutputStream
* object are written transitively so that a complete equivalent graph of
* objects can be reconstructed by an ObjectInputStream.
*
+ * The difference between fastSerialzation and default serialization is the
+ * descriptor serialization. The data serialization is same with each other.
+ *
* <p>Exceptions are thrown for problems with the OutputStream and for
* classes that should not be serialized. All exceptions are fatal to the
* OutputStream, which is left in an indeterminate state, and it is up to
@@ -633,7 +672,11 @@ public class ObjectOutputStream
* stream
*/
protected void writeStreamHeader() throws IOException {
- bout.writeShort(STREAM_MAGIC);
+ if (useFastSerializer) {
+ bout.writeShort(STREAM_MAGIC_FAST);
+ } else {
+ bout.writeShort(STREAM_MAGIC);
+ }
bout.writeShort(STREAM_VERSION);
}
@@ -648,6 +691,9 @@ public class ObjectOutputStream
* By default, this method writes class descriptors according to the format
* defined in the Object Serialization specification.
*
+ * In fastSerializer mode, we will only write the classname to the stream.
+ * The annotateClass is used to match the resolveClass in readClassDescriptor.
+ *
* <p>Note that this method will only be called if the ObjectOutputStream
* is not using the old serialization stream format (set by calling
* ObjectOutputStream's <code>useProtocolVersion</code> method). If this
@@ -665,7 +711,14 @@ public class ObjectOutputStream
protected void writeClassDescriptor(ObjectStreamClass desc)
throws IOException
{
- desc.writeNonProxy(this);
+ if (useFastSerializer) {
+ writeUTF(desc.getName());
+ // The annotateClass is used to match the resolveClass called in
+ // readClassDescriptor.
+ annotateClass(desc.forClass());
+ } else {
+ desc.writeNonProxy(this);
+ }
}
/**
@@ -1275,9 +1328,21 @@ public class ObjectOutputStream
bout.writeByte(TC_CLASSDESC);
handles.assign(unshared ? null : desc);
+ if (Logging.fastSerLogger != null) {
+ Logging.fastSerLogger.fine(
+ "[Serialize] useFastSerializer:{0}, Class name:{1}, SerialVersionUID:{2}, flags:{3}, protocol:{4}",
+ useFastSerializer, desc.getName(), desc.getSerialVersionUID(), desc.getFlags(this), protocol);
+ }
+
if (protocol == PROTOCOL_VERSION_1) {
// do not invoke class descriptor write hook with old protocol
- desc.writeNonProxy(this);
+ if (useFastSerializer) {
+ // only write name and annotate class when using FastSerializer
+ writeUTF(desc.getName());
+ annotateClass(desc.forClass());
+ } else {
+ desc.writeNonProxy(this);
+ }
} else {
writeClassDescriptor(desc);
}
@@ -1291,7 +1356,9 @@ public class ObjectOutputStream
bout.setBlockDataMode(false);
bout.writeByte(TC_ENDBLOCKDATA);
- writeClassDesc(desc.getSuperDesc(), false);
+ if (!useFastSerializer) {
+ writeClassDesc(desc.getSuperDesc(), false);
+ }
}
/**
diff --git a/jdk/src/share/classes/java/io/ObjectStreamClass.java b/jdk/src/share/classes/java/io/ObjectStreamClass.java
index 64453b25a..fce3c3475 100644
--- a/jdk/src/share/classes/java/io/ObjectStreamClass.java
+++ b/jdk/src/share/classes/java/io/ObjectStreamClass.java
@@ -280,6 +280,40 @@ public class ObjectStreamClass implements Serializable {
return suid.longValue();
}
+ /**
+ * Return the flags for this class described by this descriptor. The flags
+ * means a set of bit masks for ObjectStreamClass, which indicate the status
+ * of SC_WRITE_METHOD, SC_SERIALIZABLE, SC_EXTERNALIZABLE, SC_BLOCK_DATA and
+ * SC_ENUM.
+ *
+ * @param serialStream ObjectOutputStream or ObjectInputStream
+ *
+ * @return the flags for this class described by this descriptor
+ */
+ public byte getFlags(Object serialStream) {
+ byte flags = 0;
+ if (externalizable) {
+ flags |= ObjectStreamConstants.SC_EXTERNALIZABLE;
+ if (serialStream instanceof ObjectOutputStream) {
+ int protocol = ((ObjectOutputStream)serialStream).getProtocolVersion();
+ if (protocol != ObjectStreamConstants.PROTOCOL_VERSION_1) {
+ flags |= ObjectStreamConstants.SC_BLOCK_DATA;
+ }
+ } else if (serialStream instanceof ObjectInputStream) {
+ flags |= ObjectStreamConstants.SC_BLOCK_DATA;
+ }
+ } else if (serializable) {
+ flags |= ObjectStreamConstants.SC_SERIALIZABLE;
+ }
+ if (hasWriteObjectData) {
+ flags |= ObjectStreamConstants.SC_WRITE_METHOD;
+ }
+ if (isEnum) {
+ flags |= ObjectStreamConstants.SC_ENUM;
+ }
+ return flags;
+ }
+
/**
* Return the class in the local VM that this version is mapped to. Null
* is returned if there is no corresponding local class.
@@ -570,6 +604,15 @@ public class ObjectStreamClass implements Serializable {
ObjectStreamClass() {
}
+ /**
+ * Create a blank class descriptor with name. It is only used
+ * in fastSerialize path.
+ * @param name class name
+ */
+ ObjectStreamClass(String name) {
+ this.name = name;
+ }
+
/**
* Creates a PermissionDomain that grants no permission.
*/
@@ -756,6 +799,44 @@ public class ObjectStreamClass implements Serializable {
initialized = true;
}
+ /**
+ * Initializes class descriptor representing a non-proxy class.
+ * Used in fast serialization mode.
+ */
+ void initNonProxyFast(ObjectStreamClass model,
+ ClassNotFoundException resolveEx)
+ {
+ this.cl = model.cl;
+ this.resolveEx = resolveEx;
+ this.superDesc = model.superDesc;
+ name = model.name;
+ this.suid = model.suid;
+ isProxy = false;
+ isEnum = model.isEnum;
+ serializable = model.serializable;
+ externalizable = model.externalizable;
+ hasBlockExternalData = model.hasBlockExternalData;
+ hasWriteObjectData = model.hasWriteObjectData;
+ fields = model.fields;
+ primDataSize = model.primDataSize;
+ numObjFields = model.numObjFields;
+
+ writeObjectMethod = model.writeObjectMethod;
+ readObjectMethod = model.readObjectMethod;
+ readObjectNoDataMethod = model.readObjectNoDataMethod;
+ writeReplaceMethod = model.writeReplaceMethod;
+ readResolveMethod = model.readResolveMethod;
+ if (deserializeEx == null) {
+ deserializeEx = model.deserializeEx;
+ }
+ domains = model.domains;
+ cons = model.cons;
+ fieldRefl = model.fieldRefl;
+ localDesc = model;
+
+ initialized = true;
+ }
+
/**
* Reads non-proxy class descriptor information from given input stream.
* The resulting class descriptor is not fully functional; it can only be
diff --git a/jdk/src/share/classes/java/io/ObjectStreamConstants.java b/jdk/src/share/classes/java/io/ObjectStreamConstants.java
index 23f72b436..59179a6ec 100644
--- a/jdk/src/share/classes/java/io/ObjectStreamConstants.java
+++ b/jdk/src/share/classes/java/io/ObjectStreamConstants.java
@@ -38,6 +38,11 @@ public interface ObjectStreamConstants {
*/
final static short STREAM_MAGIC = (short)0xaced;
+ /**
+ * Magic number that is written to the stream header when using fastserilizer.
+ */
+ static final short STREAM_MAGIC_FAST = (short)0xdeca;
+
/**
* Version number that is written to the stream header.
*/
diff --git a/jdk/src/share/classes/sun/misc/Unsafe.java b/jdk/src/share/classes/sun/misc/Unsafe.java
index 99e465802..92fb01669 100644
--- a/jdk/src/share/classes/sun/misc/Unsafe.java
+++ b/jdk/src/share/classes/sun/misc/Unsafe.java
@@ -433,6 +433,8 @@ public final class Unsafe {
/** @see #putByte(long, byte) */
public native void putDouble(long address, double x);
+ public native boolean getUseFastSerializer();
+
/**
* Fetches a native pointer from a given memory address. If the address is
* zero, or does not point into a block obtained from {@link

View File

@ -0,0 +1,24 @@
From 82250c7c4978bf7591299e8635fb183f36d3546f Mon Sep 17 00:00:00 2001
Date: Fri, 19 Apr 2019 16:30:04 +0000
Subject: [PATCH] fix crash in JVMTI debug
---
hotspot/src/share/vm/prims/jvmtiEnvBase.cpp | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/hotspot/src/share/vm/prims/jvmtiEnvBase.cpp b/hotspot/src/share/vm/prims/jvmtiEnvBase.cpp
index fe2a3811..5db41567 100644
--- a/hotspot/src/share/vm/prims/jvmtiEnvBase.cpp
+++ b/hotspot/src/share/vm/prims/jvmtiEnvBase.cpp
@@ -1092,7 +1092,7 @@ JvmtiEnvBase::get_object_monitor_usage(JavaThread* calling_thread, jobject objec
// If the monitor has no owner, then a non-suspended contending
// thread could potentially change the state of the monitor by
// entering it. The JVM/TI spec doesn't allow this.
- if (owning_thread == NULL && !at_safepoint &
+ if (owning_thread == NULL && !at_safepoint &&
!JvmtiEnv::is_thread_fully_suspended(pending_thread, true, &debug_bits)) {
if (ret.owner != NULL) {
destroy_jni_reference(calling_thread, ret.owner);
--
2.19.0

View File

@ -0,0 +1,37 @@
From 7c73365615f00951272310db44dec2939b91b48e Mon Sep 17 00:00:00 2001
Date: Wed, 19 Feb 2020 19:09:39 +0000
Subject: [PATCH] fix incorrect offset for oop field with weak memory model
Summary: <interpreter>: add loadload membar in fast_storefield and fast_accessfield to avoid loading a incorrect offset
LLT: N/A
Bug url: N/A
---
hotspot/src/cpu/aarch64/vm/templateTable_aarch64.cpp | 5 +++++
1 file changed, 5 insertions(+)
diff --git a/hotspot/src/cpu/aarch64/vm/templateTable_aarch64.cpp b/hotspot/src/cpu/aarch64/vm/templateTable_aarch64.cpp
index 5a619566..aa9545ee 100644
--- a/hotspot/src/cpu/aarch64/vm/templateTable_aarch64.cpp
+++ b/hotspot/src/cpu/aarch64/vm/templateTable_aarch64.cpp
@@ -2922,6 +2922,8 @@ void TemplateTable::fast_storefield(TosState state)
// access constant pool cache
__ get_cache_and_index_at_bcp(r2, r1, 1);
+ __ membar(MacroAssembler::LoadLoad);
+
// test for volatile with r3
__ ldrw(r3, Address(r2, in_bytes(base +
ConstantPoolCacheEntry::flags_offset())));
@@ -3013,6 +3015,9 @@ void TemplateTable::fast_accessfield(TosState state)
// access constant pool cache
__ get_cache_and_index_at_bcp(r2, r1, 1);
+
+ __ membar(MacroAssembler::LoadLoad);
+
__ ldr(r1, Address(r2, in_bytes(ConstantPoolCache::base_offset() +
ConstantPoolCacheEntry::f2_offset())));
__ ldrw(r3, Address(r2, in_bytes(ConstantPoolCache::base_offset() +
--
2.19.0

View File

@ -1,5 +1,5 @@
#!/bin/bash
# Generates the 'source tarball' for JDK 8 projects.
# Generates the 'source tarball' for jdk8u projects.
#
# Example:
# When used from local repo set REPO_ROOT pointing to file:// with your repo
@ -111,31 +111,31 @@ do
hg clone ${REPO_ROOT}/${subrepo} -r ${VERSION}
done
if [ -d jdk ]; then
echo "Removing EC source code we don't build"
rm -vf jdk/src/share/native/sun/security/ec/impl/ec2.h
rm -vf jdk/src/share/native/sun/security/ec/impl/ec2_163.c
rm -vf jdk/src/share/native/sun/security/ec/impl/ec2_193.c
rm -vf jdk/src/share/native/sun/security/ec/impl/ec2_233.c
rm -vf jdk/src/share/native/sun/security/ec/impl/ec2_aff.c
rm -vf jdk/src/share/native/sun/security/ec/impl/ec2_mont.c
rm -vf jdk/src/share/native/sun/security/ec/impl/ecp_192.c
rm -vf jdk/src/share/native/sun/security/ec/impl/ecp_224.c
echo "Syncing EC list with NSS"
if [ "x$PR3756" = "x" ] ; then
# get pr3756.patch (from http://icedtea.classpath.org/hg/icedtea8) from most correct tag
# Do not push it or publish it (see http://icedtea.classpath.org/bugzilla/show_bug.cgi?id=3756)
wget http://icedtea.classpath.org/hg/icedtea8/raw-file/tip/patches/pr3756.patch
patch -Np1 < pr3756.patch
rm pr3756.patch
else
echo "Applying ${PR3756}"
patch -Np1 < $PR3756
fi;
fi
find . -name '*.orig' -exec rm -vf '{}' ';'
#if [ -d jdk ]; then
#echo "Removing EC source code we don't build"
#rm -vf jdk/src/share/native/sun/security/ec/impl/ec2.h
#rm -vf jdk/src/share/native/sun/security/ec/impl/ec2_163.c
#rm -vf jdk/src/share/native/sun/security/ec/impl/ec2_193.c
#rm -vf jdk/src/share/native/sun/security/ec/impl/ec2_233.c
#rm -vf jdk/src/share/native/sun/security/ec/impl/ec2_aff.c
#rm -vf jdk/src/share/native/sun/security/ec/impl/ec2_mont.c
#rm -vf jdk/src/share/native/sun/security/ec/impl/ecp_192.c
#rm -vf jdk/src/share/native/sun/security/ec/impl/ecp_224.c
#
#echo "Syncing EC list with NSS"
#
#if [ "x$PR3756" = "x" ] ; then
## get pr3756.patch (from http://icedtea.classpath.org/hg/icedtea8) from most correct tag
## Do not push it or publish it (see http://icedtea.classpath.org/bugzilla/show_bug.cgi?id=3756)
# wget http://icedtea.classpath.org/hg/icedtea8/raw-file/tip/patches/pr3756.patch
# patch -Np1 < pr3756.patch
# rm pr3756.patch
#else
# echo "Applying ${PR3756}"
# patch -Np1 < $PR3756
#fi;
#fi
#find . -name '*.orig' -exec rm -vf '{}' ';'
popd
echo "Compressing remaining forest"
@ -150,5 +150,3 @@ mv ${TARBALL_NAME} ..
popd
echo "Done. You may want to remove the uncompressed version."

View File

@ -77,7 +77,7 @@
%global bootstrap_build 0
%endif
%global release_targets images zip-docs
%global release_targets images docs-zip
# No docs nor bootcycle for debug builds
%global debug_targets images
@ -148,7 +148,7 @@
# Define old aarch64/jdk8u tree variables for compatibility
%global project aarch64-port
%global repo jdk8u-shenandoah
%global revision aarch64-shenandoah-jdk8u265-b01
%global revision aarch64-shenandoah-jdk8u272-b10
%global full_revision %{project}-%{repo}-%{revision}
# Define IcedTea version used for SystemTap tapsets and desktop files
%global icedteaver 3.15.0
@ -915,7 +915,7 @@ Provides: java-%{javaver}-%{origin}-accessibility%{?1} = %{epoch}:%{version}-%{r
Name: java-%{javaver}-%{origin}
Version: %{javaver}.%{updatever}.%{buildver}
Release: 2
Release: 0
# java-1.5.0-ibm from jpackage.org set Epoch to 1 for unknown reasons
# and this change was brought into RHEL-4. java-1.5.0-ibm packages
# also included the epoch in their virtual provides. This created a
@ -973,12 +973,9 @@ Patch1: 8160300.patch
Patch8: replace-vector-to-improve-performance-of-xml.validat.patch
Patch9: AARCH64-fix-itable-stub-code-size-limit.patch
Patch10: 8221658.patch
Patch11: 8148754-C2-loop-unrolling-fails-due-to-unexpected-gr.patch
Patch12: add-debuginfo-for-libsaproc-on-aarch64.patch
Patch13: 8171537.patch
Patch18: fix-vendor-info.patch
Patch21: 8202952-C2-Unexpected-dead-nodes-after-matching.patch
Patch22: 8161072.patch
Patch24: 8134883.patch
Patch25: FromCardCache-default-card-index-can-cause.patch
Patch26: disable-UseLSE-on-ARMv8.1-by-default.patch
@ -987,7 +984,6 @@ Patch28: 8194246.patch
Patch29: 8214345.patch
Patch30: 8191483.patch
Patch31: 8141356.patch
Patch32: 8151788.patch
Patch33: 8166253.patch
Patch34: 8191955.patch
Patch35: 8186042-OopmapCache-implementation.patch
@ -995,13 +991,10 @@ Patch36: 8060463.patch
Patch37: 8131600.patch
Patch38: 8138971.patch
Patch40: 8129626.patch
Patch41: 8203699-java-lang-invoke-SpecialInte.patch
Patch45: 8191129.patch
Patch46: 8182036.patch
Patch47: 8166197.patch
Patch48: 8158946-JDK-8165808-JDK-8166583-JDK-.patch
Patch51: add-with-company-name-option.patch
Patch56: 8160369.patch
Patch57: 8031085.patch
Patch58: Reduce-the-probability-of-the-crash-related-to-ciObj.patch
Patch62: 8165857-CMS-_overflow_list-is-missing-volatile-speci.patch
@ -1012,7 +1005,6 @@ Patch70: 8164948.patch
Patch72: inline-optimize-for-aarch64.patch
# 8u242
Patch73: PS-GC-adding-acquire_size-method-for-PSParallelCompa.patch
Patch74: 8191915-java.lang.Math.multiplyExact-not-throw-an-ex.patch
Patch75: Add-ability-to-configure-third-port-for-remote-JMX.patch
Patch76: 8203196-C1-emits-incorrect-code-due-to-integer-overf.patch
@ -1037,12 +1029,28 @@ Patch95: 8205921-Optimizing-best-of-2-work-stealing-queue-selection.patch
# 8u265
Patch96: fix-Long-cache-range-and-remove-VM-option-java.lang.IntegerCache.high-by-default.patch
Patch97: leaf-optimize-in-ParallelScanvageGC.patch
Patch98: 8046294-Generate-the-4-byte-timestamp-randomly.patch
Patch100: 8203481-Incorrect-constraint-for-unextended_sp-in-frame-safe_for_sender.patch
Patch102: fix-LongCache-s-range-when-BoxTypeCachedMax-number-is-bigger-than-Integer.MAX_VALUE.patch
Patch103: Ddot-intrinsic-implement.patch
Patch104: 8234003-Improve-IndexSet-iteration.patch
Patch105: 8220159-Optimize-various-RegMask-operations-by-introducing-watermarks.patch
Patch106: fast-serializer-jdk8.patch
Patch107: 6896810-Pin.java-fails-with-OOME-during-System.out.p.patch
Patch108: 8231631-sun-net-ftp-FtpURLConnectionLeak.java-fails-.patch
Patch109: Test8167409.sh-fails-to-run-with-32bit-jdk-on-64bit-.patch
Patch111: The-runok-method-retrying-another-port-does-not-take.patch
Patch112: 8048210-8056152-fix-assert-fail-for-an-InnocuousThre.patch
Patch113: 8160425-Vectorization-with-signalling-NaN-returns-wr.patch
Patch114: 8181503-Can-t-compile-hotspot-with-c-11.patch
Patch115: 8243670-Unexpected-test-result-caused-by-C2-MergeMem.patch
Patch116: fix-crash-in-JVMTI-debug.patch
Patch118: Fix-LineBuffer-vappend-when-buffer-too-small.patch
Patch121: Remove-unused-GenericTaskQueueSet-T-F-tasks.patch
Patch122: optimize-jmap-F-dump-xxx.patch
Patch123: recreate-.java_pid-file-when-deleted-for-attach-mechanism.patch
Patch124: Support-Git-commit-ID-in-the-SOURCE-field-of-the-release.patch
Patch125: Extend-CDS-to-support-app-class-metadata-sharing.patch
Patch126: zlib-optimization.patch
Patch127: add-DumpSharedSpace-guarantee-when-create-anonymous-classes.patch
#############################################
#
@ -1066,7 +1074,6 @@ Patch539: pr2888-openjdk_should_check_for_system_cacerts_database_eg_etc_pki_jav
# to OpenJDK 8u.
#############################################
# S8154313: Generated javadoc scattered all over the place
Patch578: jdk8154313-generated_javadoc_scattered_all_over_the_place.patch
# 8035341: Allow using a system installed libpng
# Patch202: jdk8035341-allow_using_system_installed_libpng.patch
# 8042159: Allow using a system-installed lcms2
@ -1382,12 +1389,9 @@ pushd %{top_level_dir_name}
%patch8 -p1
%patch9 -p1
%patch10 -p1
%patch11 -p1
%patch12 -p1
%patch13 -p1
%patch18 -p1
%patch21 -p1
%patch22 -p1
%patch24 -p1
%patch25 -p1
%patch26 -p1
@ -1396,7 +1400,6 @@ pushd %{top_level_dir_name}
%patch29 -p1
%patch30 -p1
%patch31 -p1
%patch32 -p1
%patch33 -p1
%patch34 -p1
%patch35 -p1
@ -1404,13 +1407,10 @@ pushd %{top_level_dir_name}
%patch37 -p1
%patch38 -p1
%patch40 -p1
%patch41 -p1
%patch45 -p1
%patch46 -p1
%patch47 -p1
%patch48 -p1
%patch51 -p1
%patch56 -p1
%patch57 -p1
%patch58 -p1
%patch62 -p1
@ -1419,7 +1419,6 @@ pushd %{top_level_dir_name}
%patch68 -p1
%patch70 -p1
%patch72 -p1
%patch73 -p1
%patch74 -p1
%patch75 -p1
%patch76 -p1
@ -1438,13 +1437,28 @@ pushd %{top_level_dir_name}
%patch95 -p1
%patch96 -p1
%patch97 -p1
%patch98 -p1
%patch100 -p1
%patch102 -p1
%patch103 -p1
%patch104 -p1
%patch105 -p1
%patch106 -p1
%patch107 -p1
%patch108 -p1
%patch109 -p1
%patch111 -p1
%patch112 -p1
%patch113 -p1
%patch114 -p1
%patch115 -p1
%patch116 -p1
%patch118 -p1
%patch121 -p1
%patch122 -p1
%patch123 -p1
%patch124 -p1
%patch125 -p1
%patch126 -p1
%patch127 -p1
popd
@ -1453,9 +1467,6 @@ popd
# %patch202
# %patch203
# Upstreamable fixes
%patch578
# RPM-only fixes
%patch1000
@ -2064,6 +2075,52 @@ require "copy_jdk_configs.lua"
%endif
%changelog
* Fri Oct 23 2020 <guoge1@huawei.com> - 1:1.8.0.272-b10.0
- updated to aarch64-shenandoah-jdk8u272-b10 (from aarch64-port/jdk8u-shenandoah)
- deleted: 8046294-Generate-the-4-byte-timestamp-randomly.patch
- deleted: 8148754-C2-loop-unrolling-fails-due-to-unexpected-gr.patch
- deleted: 8151788.patch
- deleted: 8161072.patch
- deleted: 8171537.patch
- deleted: 8203481-Incorrect-constraint-for-unextended_sp-in-frame-safe_for_sender.patch
- deleted: 8203699-java-lang-invoke-SpecialInte.patch
- modified: Extend-CDS-to-support-app-class-metadata-sharing.patch
- deleted: Test-SSLSocketSSLEngineTemplate.java-intermittent-fa.patch
- modified: fast-serializer-jdk8.patch
- deleted: fix-CompactibleFreeListSpace-block_size-crash.patch
- deleted: fix-incorrect-klass-field-in-oop-with-weak-memory-model.patch
* Mon Sep 21 2020 noah <hedongbo@huawei.com> -:1.8.0.265-b10.6
- add add-DumpSharedSpace-guarantee-when-create-anonymous-classes.patch
* Fri Sep 11 2020 noah <hedongbo@huawei.com> -:1.8.0.265-b10.5
- add 6896810-Pin.java-fails-with-OOME-during-System.out.p.patch
- add 8231631-sun-net-ftp-FtpURLConnectionLeak.java-fails-.patch
- add Test8167409.sh-fails-to-run-with-32bit-jdk-on-64bit-.patch
- add Test-SSLSocketSSLEngineTemplate.java-intermittent-fa.patch
- add The-runok-method-retrying-another-port-does-not-take.patch
- add 8048210-8056152-fix-assert-fail-for-an-InnocuousThre.patch
- add 8160425-Vectorization-with-signalling-NaN-returns-wr.patch
- add 8181503-Can-t-compile-hotspot-with-c-11.patch
- add 8243670-Unexpected-test-result-caused-by-C2-MergeMem.patch
- add fix-crash-in-JVMTI-debug.patch
- add fix-incorrect-klass-field-in-oop-with-weak-memory-model.patch
- add Fix-LineBuffer-vappend-when-buffer-too-small.patch
- add make-disable-precompiled-headers-work.patch
- add fix-CompactibleFreeListSpace-block_size-crash.patch
- add Remove-unused-GenericTaskQueueSet-T-F-tasks.patch
- add optimize-jmap-F-dump-xxx.patch
- add recreate-.java_pid-file-when-deleted-for-attach-mechanism.patch
- add Support-Git-commit-ID-in-the-SOURCE-field-of-the-release.patch
- add Extend-CDS-to-support-app-class-metadata-sharing.patch
- add zlib-optimization.patch
* Tue Sep 8 2020 noah <hedongbo@huawei.com> - 1:1.8.0.265-b10.4
- add fast-serializer-jdk8.patch
* Mon Sep 7 2020 noah <hedongbo@huawei.com> - 1:1.8.0.265-b10.3
- Delete some file header information
* Mon Sep 1 2020 jdkboy <guoge1@huawei.com> - 1:1.8.0.265-b10.2
- Remove fast-serializer-jdk8.patch

View File

@ -1,68 +0,0 @@
--- jdk8/make/Javadoc.gmk 2016-04-01 16:53:41.069477682 +0200
+++ jdk8/make/Javadoc.gmk 2016-04-01 16:53:41.014477059 +0200
@@ -220,6 +220,12 @@
JRE_API_DOCSDIR = $(DOCSDIR)/jre/api
PLATFORM_DOCSDIR = $(DOCSDIR)/platform
+
+JAVADOC_ARCHIVE_NAME := jdk-$(FULL_VERSION)-docs.zip
+JAVADOC_ARCHIVE_ASSEMBLY_DIR := $(DOCSTMPDIR)/zip-docs
+JAVADOC_ARCHIVE_DIR := $(OUTPUT_ROOT)/bundles
+JAVADOC_ARCHIVE := $(JAVADOC_ARCHIVE_DIR)/$(JAVADOC_ARCHIVE_NAME)
+
# The non-core api javadocs need to be able to access the root of the core
# api directory, so for jdk/api or jre/api to get to the core api/
# directory we would use this:
@@ -319,6 +325,37 @@
all: docs
docs: coredocs otherdocs
+#
+# Optional target which bundles all generated javadocs into a zip
+# archive. The dependency on docs is handled in Main.gmk. Incremental
+# building of docs is currently broken so if you invoke zip-docs after
+# docs, the docs are always rebuilt.
+#
+
+zip-docs: $(JAVADOC_ARCHIVE)
+
+#
+# Add the core docs as prerequisite to the archive to trigger a rebuild
+# if the core docs were rebuilt. Ideally any doc rebuild should trigger
+# this, but the way prerequisites are currently setup in this file, that
+# is hard to achieve.
+#
+
+$(JAVADOC_ARCHIVE): $(COREAPI_INDEX_FILE)
+ @$(ECHO) "Compressing javadoc to single $(JAVADOC_ARCHIVE_NAME)" ;
+ $(MKDIR) -p $(JAVADOC_ARCHIVE_DIR) ;
+ $(RM) -r $(JAVADOC_ARCHIVE_ASSEMBLY_DIR) ;
+ $(MKDIR) -p $(JAVADOC_ARCHIVE_ASSEMBLY_DIR);
+ all_roots=`$(FIND) $(DOCSDIR) | $(GREP) index.html `; \
+ pushd $(JAVADOC_ARCHIVE_ASSEMBLY_DIR); \
+ for index_file in $${all_roots} ; do \
+ target_dir=`dirname $${index_file}`; \
+ name=`$(ECHO) $${target_dir} | $(SED) "s;/spec;;" | $(SED) "s;.*/;;"`; \
+ $(LN) -s $${target_dir} $${name}; \
+ done; \
+ $(ZIP) -q -r $(JAVADOC_ARCHIVE) * ; \
+ popd ;
+
#################################################################
# Production Targets -- USE THESE TARGETS WHEN:
# a) You're generating docs outside of release engineering's
--- jdk8/make/Main.gmk 2016-04-01 16:53:41.311480424 +0200
+++ jdk8/make/Main.gmk 2016-04-01 16:53:41.266479914 +0200
@@ -165,6 +165,12 @@
@($(CD) $(SRC_ROOT)/make && $(BUILD_LOG_WRAPPER) $(MAKE) $(MAKE_ARGS) -f Javadoc.gmk docs)
@$(call TargetExit)
+zip-docs: docs zip-docs-only
+zip-docs-only: start-make
+ @$(call TargetEnter)
+ @($(CD) $(SRC_ROOT)/make && $(BUILD_LOG_WRAPPER) $(MAKE) $(MAKE_ARGS) -f Javadoc.gmk zip-docs)
+ @$(call TargetExit)
+
sign-jars: jdk sign-jars-only
sign-jars-only: start-make
@$(call TargetEnter)

View File

@ -0,0 +1,41 @@
From 16d2fb7faaaad6ae1d3f508af0c654c5c83bf484 Mon Sep 17 00:00:00 2001
Date: Tue, 8 Sep 2020 09:13:31 +0800
Subject: [PATCH] make disable precompiled headers work
Summary: <runtime>:make disable precompiled headers work
LLT: N/A
Bug url:
---
hotspot/src/share/vm/oops/oop.hpp | 2 +-
hotspot/src/share/vm/oops/oop.inline.hpp | 2 +-
2 files changed, 2 insertions(+), 2 deletions(-)
diff --git a/hotspot/src/share/vm/oops/oop.hpp b/hotspot/src/share/vm/oops/oop.hpp
index 41a7bce4d..8a33412ec 100644
--- a/hotspot/src/share/vm/oops/oop.hpp
+++ b/hotspot/src/share/vm/oops/oop.hpp
@@ -91,7 +91,7 @@ class oopDesc {
narrowKlass* compressed_klass_addr();
void set_klass(Klass* k);
- inline void release_set_klass(Klass* k);
+ void release_set_klass(Klass* k);
// For klass field compression
int klass_gap() const;
diff --git a/hotspot/src/share/vm/oops/oop.inline.hpp b/hotspot/src/share/vm/oops/oop.inline.hpp
index c3abdb128..3e3883cb6 100644
--- a/hotspot/src/share/vm/oops/oop.inline.hpp
+++ b/hotspot/src/share/vm/oops/oop.inline.hpp
@@ -141,7 +141,7 @@ inline void oopDesc::set_klass(Klass* k) {
}
}
-void oopDesc::release_set_klass(Klass* k) {
+inline void oopDesc::release_set_klass(Klass* k) {
CHECK_SET_KLASS(k);
if (UseCompressedClassPointers) {
OrderAccess::release_store(compressed_klass_addr(),
--
2.12.3

View File

@ -0,0 +1,42 @@
From 12ec07c99ff937953c3adafc12818136d9fb1d2b Mon Sep 17 00:00:00 2001
Date: Thu, 9 Apr 2020 09:18:13 +0000
Subject: [PATCH] optimize jmap -F -dump:xxx
Summary: optimize jmap -F -dump:xxx to speed up the dump process
LLT: N/A
Bug url: N/A
---
.../share/classes/sun/jvm/hotspot/oops/Metadata.java | 10 +++++++++-
1 file changed, 9 insertions(+), 1 deletion(-)
diff --git a/hotspot/agent/src/share/classes/sun/jvm/hotspot/oops/Metadata.java b/hotspot/agent/src/share/classes/sun/jvm/hotspot/oops/Metadata.java
index 4fc2ed8c..2e56d270 100644
--- a/hotspot/agent/src/share/classes/sun/jvm/hotspot/oops/Metadata.java
+++ b/hotspot/agent/src/share/classes/sun/jvm/hotspot/oops/Metadata.java
@@ -45,6 +45,7 @@ abstract public class Metadata extends VMObject {
}
private static VirtualBaseConstructor<Metadata> metadataConstructor;
+ private static Map map = new HashMap();
private static synchronized void initialize(TypeDataBase db) throws WrongTypeException {
metadataConstructor = new VirtualBaseConstructor<Metadata>(db, db.lookupType("Metadata"), null, null);
@@ -65,7 +66,14 @@ abstract public class Metadata extends VMObject {
}
public static Metadata instantiateWrapperFor(Address addr) {
- return metadataConstructor.instantiateWrapperFor(addr);
+ Metadata metadata;
+ if (!map.containsKey(addr)) {
+ metadata = metadataConstructor.instantiateWrapperFor(addr);
+ map.put(addr, metadata);
+ } else {
+ metadata = (Metadata)map.get(addr);
+ }
+ return metadata;
}
public void iterate(MetadataVisitor visitor) {
--
2.19.0

View File

@ -0,0 +1,75 @@
From 9f8ee6d44e254da38605d3ceb527d412a208c862 Mon Sep 17 00:00:00 2001
Date: Wed, 12 Aug 2020 12:09:15 +0000
Subject: [PATCH] recreate .java_pid file when deleted for attach mechanism
Summary: <hotspot>: <enable attach mechanism when .java_pid is lost>
LLT:
Bug url:
---
hotspot/src/os/linux/vm/attachListener_linux.cpp | 20 ++++++++++++++++----
hotspot/src/share/vm/services/attachListener.cpp | 1 +
hotspot/src/share/vm/services/attachListener.hpp | 2 +-
3 files changed, 18 insertions(+), 5 deletions(-)
diff --git a/hotspot/src/os/linux/vm/attachListener_linux.cpp b/hotspot/src/os/linux/vm/attachListener_linux.cpp
index 700a09ff0..1ca089740 100644
--- a/hotspot/src/os/linux/vm/attachListener_linux.cpp
+++ b/hotspot/src/os/linux/vm/attachListener_linux.cpp
@@ -485,13 +485,25 @@ bool AttachListener::init_at_startup() {
// If the file .attach_pid<pid> exists in the working directory
// or /tmp then this is the trigger to start the attach mechanism
bool AttachListener::is_init_trigger() {
- if (init_at_startup() || is_initialized()) {
- return false; // initialized at startup or already initialized
+ if (init_at_startup()) {
+ return false; // initialized at startup
}
- char fn[PATH_MAX+1];
- sprintf(fn, ".attach_pid%d", os::current_process_id());
+
+ char fn[PATH_MAX + 1];
int ret;
struct stat64 st;
+
+ // check initialized
+ if (is_initialized()) {
+ // check .java_pid file exists
+ RESTARTABLE(::stat64(LinuxAttachListener::path(), &st), ret);
+ if (ret == -1) {
+ ::shutdown(LinuxAttachListener::listener(), SHUT_RDWR);
+ }
+ return false;
+ }
+
+ sprintf(fn, ".attach_pid%d", os::current_process_id());
RESTARTABLE(::stat64(fn, &st), ret);
if (ret == -1) {
snprintf(fn, sizeof(fn), "%s/.attach_pid%d",
diff --git a/hotspot/src/share/vm/services/attachListener.cpp b/hotspot/src/share/vm/services/attachListener.cpp
index 59b2f5483..0f51378dd 100644
--- a/hotspot/src/share/vm/services/attachListener.cpp
+++ b/hotspot/src/share/vm/services/attachListener.cpp
@@ -425,6 +425,7 @@ static void attach_listener_thread_entry(JavaThread* thread, TRAPS) {
for (;;) {
AttachOperation* op = AttachListener::dequeue();
if (op == NULL) {
+ AttachListener::set_initialized(false);
return; // dequeue failed or shutdown
}
diff --git a/hotspot/src/share/vm/services/attachListener.hpp b/hotspot/src/share/vm/services/attachListener.hpp
index 5204c4c62..11ec525c6 100644
--- a/hotspot/src/share/vm/services/attachListener.hpp
+++ b/hotspot/src/share/vm/services/attachListener.hpp
@@ -71,7 +71,7 @@ class AttachListener: AllStatic {
public:
static bool is_initialized() { return _initialized; }
- static void set_initialized() { _initialized = true; }
+ static void set_initialized(bool init = true) { _initialized = init; }
// indicates if this VM supports attach-on-demand
static bool is_attach_supported() { return !DisableAttachMechanism; }
--
2.12.3

View File

@ -1,2 +1,2 @@
SHA512 (tapsets-icedtea-3.15.0.tar.xz) = c752a197cb3d812d50c35e11e4722772be40096c81d2a57933e0d9b8a3c708b9c157b8108a4e33a06ca7bb81648170994408c75d6f69d5ff12785d0c31009671
SHA512 (aarch64-port-jdk8u-shenandoah-aarch64-shenandoah-jdk8u262-b10.tar.xz) = ed4e67d3b6254113cbe93f47feae2dbbc205995b7a0ec613c87d1c9fc037c9275f332bcdb9c4b7a158e27dfbecb4772671b64084e47f5d1b25ba4677b27c7096
SHA512 (tapsets-icedtea-3.15.0.tar.xz) = 36eed87c370306c715d7a9d0906a7d719d6d956d38d03fb8f2d528d22e0067cabb3a7df10e8a7c5b65b70f2c12b9a8e7078a78a3cac478b6031d42f36415b05f
SHA512 (aarch64-port-jdk8u-shenandoah-aarch64-shenandoah-jdk8u272-b10.tar.xz) = b9c84cf37cf5cadfaa0283de37a468bd87c633a91159ed67317b2ee04b125baad0b62d9354e01c9c972e4364934e12aea061757df36313114582c54d29377150

View File

@ -31,11 +31,10 @@ if [ "x$REPO_NAME" = "x" ] ; then
REPO_NAME="jdk8u-shenandoah"
fi
if [ "x$VERSION" = "x" ] ; then
VERSION="aarch64-shenandoah-jdk8u262-b10"
VERSION="aarch64-shenandoah-jdk8u272-b10"
fi
if [ "x$COMPRESSION" = "x" ] ; then
# rhel 5 needs tar.gz
COMPRESSION=xz
fi
if [ "x$FILE_NAME_ROOT" = "x" ] ; then
@ -82,7 +81,7 @@ spec_date=`date +"%a %b %d %Y"`
revision_helper=`echo ${MAIN_VERSION%-*}`
updatever=`echo ${revision_helper##*u}`
buildver=`echo ${MAIN_VERSION##*-}`
echo "* $spec_date $user_full_name <$user_name@redhat.com> - 1:1.8.0.$updatever-$RELEASE.$buildver"
echo "* $spec_date $user_full_name <$user_name@huawei.com> - 1:1.8.0.$updatever-$RELEASE.$buildver"
echo "- updated to $MAIN_VERSION (from $PROJECT_NAME/$MAIN_REPO_NAME)"
echo "- updated to $VERSION (from $PROJECT_NAME/$REPO_NAME) of hotspot"
echo "- used $FILENAME as new sources"

882
zlib-optimization.patch Normal file
View File

@ -0,0 +1,882 @@
diff --git a/jdk/make/lib/CoreLibraries.gmk b/jdk/make/lib/CoreLibraries.gmk
index c8e4815..c36ac39 100644
--- a/jdk/make/lib/CoreLibraries.gmk
+++ b/jdk/make/lib/CoreLibraries.gmk
@@ -257,6 +257,9 @@ ifeq ($(USE_EXTERNAL_LIBZ), true)
LIBZIP_EXCLUDES += zlib
else
ZLIB_CPPFLAGS := -I$(JDK_TOPDIR)/src/share/native/java/util/zip/zlib
+ ifeq ($(OPENJDK_TARGET_CPU), aarch64)
+ ZLIB_CPPFLAGS += -DCRC32_ARMV8_CRC32 -DHASH_ARMV8_CRC32 -march=armv8-a+crc -DUNALIGNED_OK -DADLER32_SIMD_NEON -DSLIDE_HASH_NEON -DINFLATE_CHUNK_SIMD_NEON -O3
+ endif
endif
BUILD_LIBZIP_REORDER :=
@@ -274,7 +277,7 @@ $(eval $(call SetupNativeCompilation,BUILD_LIBZIP, \
LIBRARY := zip, \
OUTPUT_DIR := $(INSTALL_LIBRARIES_HERE), \
LANG := C, \
- OPTIMIZATION := LOW, \
+ OPTIMIZATION := HIGHEST, \
SRC := $(JDK_TOPDIR)/src/share/native/java/util/zip, \
EXCLUDES := $(LIBZIP_EXCLUDES), \
CFLAGS := $(CFLAGS_JDKLIB) \
diff --git a/jdk/src/share/native/java/util/zip/zlib/deflate.c b/jdk/src/share/native/java/util/zip/zlib/deflate.c
index f30f71b..c018064 100644
--- a/jdk/src/share/native/java/util/zip/zlib/deflate.c
+++ b/jdk/src/share/native/java/util/zip/zlib/deflate.c
@@ -184,8 +184,16 @@ local const config configuration_table[10] = {
* characters, so that a running hash key can be computed from the previous
* key instead of complete recalculation each time.
*/
-#define UPDATE_HASH(s,h,c) (h = (((h)<<s->hash_shift) ^ (c)) & s->hash_mask)
+#if defined(HASH_ARMV8_CRC32)
+#include <arm_acle.h>
+#define UPDATE_HASH_CRC_INTERNAL(s, h, c) \
+ (h = __crc32w(0, (c) & 0xFFFFFF) & ((deflate_state *)s)->hash_mask)
+#define UPDATE_HASH(s, h, c) \
+ UPDATE_HASH_CRC_INTERNAL(s, h, *(unsigned *)((uintptr_t)(&c) - (MIN_MATCH-1)))
+#else
+#define UPDATE_HASH(s,h,c) (h = (((h)<<s->hash_shift) ^ (c)) & s->hash_mask)
+#endif
/* ===========================================================================
* Insert string str in the dictionary and set match_head to the previous head
@@ -222,6 +230,46 @@ local const config configuration_table[10] = {
* bit values at the expense of memory usage). We slide even when level == 0 to
* keep the hash table consistent if we switch back to level > 0 later.
*/
+
+#if defined(SLIDE_HASH_NEON)
+#include <arm_neon.h>
+static inline void slide_hash_chain(Pos *table, unsigned int entries, uint16_t window_size) {
+ register uint16x8_t v, *p;
+ register size_t n;
+
+ size_t size = entries * sizeof(table[0]); /* the size of hash table */
+ Assert((size % (sizeof(uint16x8_t) * 8) == 0), "hash table size err"); /* if it's not 0, size err occurs */
+
+ Assert(sizeof(Pos) == 2, "Wrong Pos size"); /* if size of Pos is not 2, release wrong size error */
+ v = vdupq_n_u16(window_size);
+
+ p = (uint16x8_t *)table;
+ n = size / (sizeof(uint16x8_t) * 8);
+ do {
+ p[0] = vqsubq_u16(p[0], v);
+ p[1] = vqsubq_u16(p[1], v);
+ p[2] = vqsubq_u16(p[2], v);
+ p[3] = vqsubq_u16(p[3], v);
+ p[4] = vqsubq_u16(p[4], v);
+ p[5] = vqsubq_u16(p[5], v);
+ p[6] = vqsubq_u16(p[6], v);
+ p[7] = vqsubq_u16(p[7], v);
+ p += 8;
+ } while (--n);
+}
+
+local void slide_hash(s)
+ deflate_state *s;
+{
+ const size_t size = s->hash_size * sizeof(s->head[0]);
+ Assert(sizeof(Pos) == 2, "Wrong Pos size."); /* if size of Pos is not 2, release wrong size error */
+ Assert((size % (sizeof(uint16x8_t)*2)) == 0, "Hash table size error."); /* if it's not 0, size err occurs */
+ slide_hash_chain(s->head, s->hash_size, s->w_size);
+#ifndef FASTEST
+ slide_hash_chain(s->prev, s->w_size, s->w_size);
+#endif
+}
+#else
local void slide_hash(s)
deflate_state *s;
{
@@ -247,6 +295,7 @@ local void slide_hash(s)
} while (--n);
#endif
}
+#endif
/* ========================================================================= */
int ZEXPORT deflateInit_(strm, level, version, stream_size)
@@ -1198,14 +1247,15 @@ local unsigned read_buf(strm, buf, size)
strm->avail_in -= len;
zmemcpy(buf, strm->next_in, len);
- if (strm->state->wrap == 1) {
- strm->adler = adler32(strm->adler, buf, len);
- }
#ifdef GZIP
- else if (strm->state->wrap == 2) {
+ if (strm->state->wrap == 2) { /* use crc32 algo */
strm->adler = crc32(strm->adler, buf, len);
- }
+ } else
#endif
+ if (strm->state->wrap == 1) {
+ strm->adler = adler32(strm->adler, buf, len);
+ }
+
strm->next_in += len;
strm->total_in += len;
diff --git a/jdk/src/share/native/java/util/zip/zlib/inffast.c b/jdk/src/share/native/java/util/zip/zlib/inffast.c
index 4bfc995..2084739 100644
--- a/jdk/src/share/native/java/util/zip/zlib/inffast.c
+++ b/jdk/src/share/native/java/util/zip/zlib/inffast.c
@@ -81,6 +81,9 @@ unsigned start; /* inflate()'s starting value for strm->avail_out */
unsigned char FAR *out; /* local strm->next_out */
unsigned char FAR *beg; /* inflate()'s initial strm->next_out */
unsigned char FAR *end; /* while out < end, enough space available */
+#if defined(INFLATE_CHUNK_SIMD_NEON)
+ unsigned char FAR *limit; /* safety limit for chunky copies */
+#endif
#ifdef INFLATE_STRICT
unsigned dmax; /* maximum distance from zlib header */
#endif
@@ -113,7 +116,12 @@ unsigned start; /* inflate()'s starting value for strm->avail_out */
#endif
wsize = state->wsize;
whave = state->whave;
+#if defined(INFLATE_CHUNK_SIMD_NEON)
+ limit = out + strm->avail_out;
+ wnext = (state->wnext == 0 && whave >= wsize) ? wsize : state->wnext;
+#else
wnext = state->wnext;
+#endif
window = state->window;
hold = state->hold;
bits = state->bits;
@@ -221,6 +229,45 @@ unsigned start; /* inflate()'s starting value for strm->avail_out */
#endif
}
from = window;
+#if defined(INFLATE_CHUNK_SIMD_NEON)
+ if (wnext >= op) { /* contiguous in window */
+ from += wnext - op;
+ }
+ else { /* wrap around window */
+ op -= wnext;
+ from += wsize - op;
+ if (op < len) { /* some from end of window */
+ len -= op;
+ out = chunkcopy_safe(out, from, op, limit);
+ from = window; /* more from start of window */
+ op = wnext;
+ /* This (rare) case can create a situation where
+ the first chunkcopy below must be checked.
+ */
+ }
+ }
+ if (op < len) { /* still need some from output */
+ out = chunkcopy_safe(out, from, op, limit);
+ len -= op;
+ /* When dist is small the amount of data that can be
+ copied from the window is also small, and progress
+ towards the dangerous end of the output buffer is
+ also small. This means that for trivial memsets and
+ for chunkunroll_relaxed() a safety check is
+ unnecessary. However, these conditions may not be
+ entered at all, and in that case it's possible that
+ the main copy is near the end.
+ */
+ out = chunkunroll_relaxed(out, &dist, &len);
+ out = chunkcopy_safe(out, out - dist, len, limit);
+ }
+ else {
+ /* from points to window, so there is no risk of
+ overlapping pointers requiring memset-like behaviour
+ */
+ out = chunkcopy_safe(out, from, len, limit);
+ }
+#else
if (wnext == 0) { /* very common case */
from += wsize - op;
if (op < len) { /* some from window */
@@ -271,8 +318,18 @@ unsigned start; /* inflate()'s starting value for strm->avail_out */
if (len > 1)
*out++ = *from++;
}
+#endif
}
- else {
+ else {
+#if defined(INFLATE_CHUNK_SIMD_NEON)
+ /* Whole reference is in range of current output. No
+ range checks are necessary because we start with room
+ for at least 258 bytes of output, so unroll and roundoff
+ operations can write beyond `out+len` so long as they
+ stay within 258 bytes of `out`.
+ */
+ out = chunkcopy_lapped_relaxed(out, dist, len);
+#else
from = out - dist; /* copy direct from output */
do { /* minimum length is three */
*out++ = *from++;
@@ -284,7 +341,8 @@ unsigned start; /* inflate()'s starting value for strm->avail_out */
*out++ = *from++;
if (len > 1)
*out++ = *from++;
- }
+ }
+#endif
}
}
else if ((op & 64) == 0) { /* 2nd level distance code */
diff --git a/jdk/src/share/native/java/util/zip/zlib/inffast.h b/jdk/src/share/native/java/util/zip/zlib/inffast.h
index b8da8bb..0def2e3 100644
--- a/jdk/src/share/native/java/util/zip/zlib/inffast.h
+++ b/jdk/src/share/native/java/util/zip/zlib/inffast.h
@@ -32,4 +32,374 @@
subject to change. Applications should only use zlib.h.
*/
+/*
+ * The chunk-copy code below deals with writing the decoded DEFLATE data to
+ * the output with SIMD methods to increase decode speed. Reading the input
+ * to the DEFLATE decoder with a wide, SIMD method can also increase decode
+ * speed. This option is supported on little endian machines, and reads the
+ * input data in 64-bit (8 byte) chunks.
+ */
+
void ZLIB_INTERNAL inflate_fast OF((z_streamp strm, unsigned start));
+
+#if defined(INFLATE_CHUNK_SIMD_NEON)
+
+#include <stdint.h>
+#include "zutil.h"
+#include <arm_neon.h>
+
+typedef uint8x16_t z_vec128i_t;
+
+#define Z_STATIC_ASSERT(name, assert) typedef char name[(assert) ? 1 : -1]
+
+#if __STDC_VERSION__ >= 199901L
+#define Z_RESTRICT restrict
+#else
+#define Z_RESTRICT
+#endif
+
+#if defined(__clang__) || defined(__GNUC__) || defined(__llvm__)
+#define Z_BUILTIN_MEMCPY __builtin_memcpy
+#else
+#define Z_BUILTIN_MEMCPY zmemcpy
+#endif
+
+/*
+ * chunk copy type: the z_vec128i_t type size should be exactly 128-bits
+ * and equal to CHUNKCOPY_CHUNK_SIZE.
+ */
+#define CHUNKCOPY_CHUNK_SIZE sizeof(z_vec128i_t)
+
+Z_STATIC_ASSERT(vector_128_bits_wide,
+ CHUNKCOPY_CHUNK_SIZE == sizeof(int8_t) * 16);
+
+/*
+ * Ask the compiler to perform a wide, unaligned load with a machinevst1q_u8
+ * instruction appropriate for the z_vec128i_t type.
+ */
+static inline z_vec128i_t loadchunk(
+ const unsigned char FAR* s)
+{
+ z_vec128i_t v;
+ Z_BUILTIN_MEMCPY(&v, s, sizeof(v));
+ return v;
+}
+
+/*
+ * Ask the compiler to perform a wide, unaligned store with a machine
+ * instruction appropriate for the z_vec128i_t type.
+ */
+static inline void storechunk(
+ unsigned char FAR* d,
+ const z_vec128i_t v)
+{
+ Z_BUILTIN_MEMCPY(d, &v, sizeof(v));
+}
+
+/*
+ * Perform a memcpy-like operation, assuming that length is non-zero and that
+ * it's OK to overwrite at least CHUNKCOPY_CHUNK_SIZE bytes of output even if
+ * the length is shorter than this.
+ *
+ * It also guarantees that it will properly unroll the data if the distance
+ * between `out` and `from` is at least CHUNKCOPY_CHUNK_SIZE, which we rely on
+ * in chunkcopy_relaxed().
+ *
+ * Aside from better memory bus utilisation, this means that short copies
+ * (CHUNKCOPY_CHUNK_SIZE bytes or fewer) will fall straight through the loop
+ * without iteration, which will hopefully make the branch prediction more
+ * reliable.
+ */
+static inline unsigned char FAR* chunkcopy_core(
+ unsigned char FAR* out,
+ const unsigned char FAR* from,
+ unsigned len)
+{
+ const int bump = (--len % CHUNKCOPY_CHUNK_SIZE) + 1;
+ storechunk(out, loadchunk(from));
+ out += bump;
+ from += bump;
+ len /= CHUNKCOPY_CHUNK_SIZE;
+ while (len-- > 0) {
+ storechunk(out, loadchunk(from));
+ out += CHUNKCOPY_CHUNK_SIZE;
+ from += CHUNKCOPY_CHUNK_SIZE;
+ }
+ return out;
+}
+
+/*
+ * Like chunkcopy_core(), but avoid writing beyond of legal output.
+ *
+ * Accepts an additional pointer to the end of safe output. A generic safe
+ * copy would use (out + len), but it's normally the case that the end of the
+ * output buffer is beyond the end of the current copy, and this can still be
+ * exploited.
+ */
+static inline unsigned char FAR* chunkcopy_core_safe(
+ unsigned char FAR* out,
+ const unsigned char FAR* from,
+ unsigned len,
+ unsigned char FAR* limit)
+{
+ Assert(out + len <= limit, "chunk copy exceeds safety limit");
+ if ((limit - out) < (ptrdiff_t) CHUNKCOPY_CHUNK_SIZE) {
+ const unsigned char FAR* Z_RESTRICT rfrom = from;
+ if (len & 8) {
+ Z_BUILTIN_MEMCPY(out, rfrom, 8);
+ out += 8;
+ rfrom += 8;
+ }
+ if (len & 4) {
+ Z_BUILTIN_MEMCPY(out, rfrom, 4);
+ out += 4;
+ rfrom += 4;
+ }
+ if (len & 2) {
+ Z_BUILTIN_MEMCPY(out, rfrom, 2);
+ out += 2;
+ rfrom += 2;
+ }
+ if (len & 1) {
+ *out++ = *rfrom++;
+ }
+ return out;
+ }
+ return chunkcopy_core(out, from, len);
+}
+
+/*
+ * Perform short copies until distance can be rewritten as being at least
+ * CHUNKCOPY_CHUNK_SIZE.
+ *
+ * Assumes it's OK to overwrite at least the first 2*CHUNKCOPY_CHUNK_SIZE
+ * bytes of output even if the copy is shorter than this. This assumption
+ * holds within zlib inflate_fast(), which starts every iteration with at
+ * least 258 bytes of output space available (258 being the maximum length
+ * output from a single token; see inffast.c).
+ */
+static inline unsigned char FAR* chunkunroll_relaxed(
+ unsigned char FAR* out,
+ unsigned FAR* dist,
+ unsigned FAR* len)
+{
+ const unsigned char FAR* from = out - *dist;
+ while (*dist < *len && *dist < CHUNKCOPY_CHUNK_SIZE) {
+ storechunk(out, loadchunk(from));
+ out += *dist;
+ *len -= *dist;
+ *dist += *dist;
+ }
+ return out;
+}
+
+/*
+ * v_load64_dup(): load *src as an unaligned 64-bit int and duplicate it in
+ * every 64-bit component of the 128-bit result (64-bit int splat).
+ */
+static inline z_vec128i_t v_load64_dup(const void* src)
+{
+ return vcombine_u8(vld1_u8(src), vld1_u8(src));
+}
+
+/*
+ * v_load32_dup(): load *src as an unaligned 32-bit int and duplicate it in
+ * every 32-bit component of the 128-bit result (32-bit int splat).
+ */
+static inline z_vec128i_t v_load32_dup(const void* src)
+{
+ int32_t i32;
+ Z_BUILTIN_MEMCPY(&i32, src, sizeof(i32));
+ return vreinterpretq_u8_s32(vdupq_n_s32(i32));
+}
+
+/*
+ * v_load16_dup(): load *src as an unaligned 16-bit int and duplicate it in
+ * every 16-bit component of the 128-bit result (16-bit int splat).
+ */
+static inline z_vec128i_t v_load16_dup(const void* src)
+{
+ int16_t i16;
+ Z_BUILTIN_MEMCPY(&i16, src, sizeof(i16));
+ return vreinterpretq_u8_s16(vdupq_n_s16(i16));
+}
+
+/*
+ * v_load8_dup(): load the 8-bit int *src and duplicate it in every 8-bit
+ * component of the 128-bit result (8-bit int splat).
+ */
+static inline z_vec128i_t v_load8_dup(const void* src)
+{
+ return vld1q_dup_u8((const uint8_t*) src);
+}
+
+/*
+ * v_store_128(): store the 128-bit vec in a memory destination (that might
+ * not be 16-byte aligned) void* out.
+ */
+static inline void v_store_128(unsigned char* out, const z_vec128i_t vec)
+{
+ vst1q_u8(out, vec);
+}
+
+/*
+ * Perform an overlapping copy which behaves as a memset() operation, but
+ * supporting periods other than one, and assume that length is non-zero and
+ * that it's OK to overwrite at least CHUNKCOPY_CHUNK_SIZE*3 bytes of output
+ * even if the length is shorter than this.
+ */
+static inline unsigned char FAR* chunkset_store_result(
+ unsigned len,
+ unsigned char FAR* out,
+ z_vec128i_t v)
+{
+ do {
+ v_store_128(out, v);
+ out += sizeof(v);
+ len -= sizeof(v);
+ } while (len > 0);
+ return out;
+}
+
+static inline unsigned char FAR* chunkset_core(unsigned char FAR* out, unsigned period, unsigned len)
+{
+ z_vec128i_t v;
+ const int bump = ((len - 1) % sizeof(v)) + 1;
+ switch (period) {
+ case 1:
+ v = v_load8_dup(out - 1);
+ v_store_128(out, v);
+ out += bump;
+ len -= bump;
+ while (len > 0) {
+ v_store_128(out, v);
+ out += sizeof(v);
+ len -= sizeof(v);
+ }
+ return out;
+ case 2:
+ v = v_load16_dup(out - 2);
+ v_store_128(out, v);
+ out += bump;
+ len -= bump;
+ if (len > 0) {
+ v = v_load16_dup(out - 2);
+ out = chunkset_store_result(len, out, v);
+ }
+ return out;
+ case 4:
+ v = v_load32_dup(out - 4);
+ v_store_128(out, v);
+ out += bump;
+ len -= bump;
+ if (len > 0) {
+ v = v_load32_dup(out - 4);
+ out = chunkset_store_result(len, out, v);
+ }
+ return out;
+ case 8:
+ v = v_load64_dup(out - 8);
+ v_store_128(out, v);
+ out += bump;
+ len -= bump;
+ if (len > 0) {
+ v = v_load64_dup(out - 8);
+ out = chunkset_store_result(len, out, v);
+ }
+ return out;
+ }
+ out = chunkunroll_relaxed(out, &period, &len);
+ return chunkcopy_core(out, out - period, len);
+}
+
+/*
+ * Perform a memcpy-like operation, but assume that length is non-zero and that
+ * it's OK to overwrite at least CHUNKCOPY_CHUNK_SIZE bytes of output even if
+ * the length is shorter than this.
+ *
+ * Unlike chunkcopy_core() above, no guarantee is made regarding the behaviour
+ * of overlapping buffers, regardless of the distance between the pointers.
+ * This is reflected in the `restrict`-qualified pointers, allowing the
+ * compiler to re-order loads and stores.
+ */
+static inline unsigned char FAR* chunkcopy_relaxed(
+ unsigned char FAR* Z_RESTRICT out,
+ const unsigned char FAR* Z_RESTRICT from,
+ unsigned len)
+{
+ return chunkcopy_core(out, from, len);
+}
+
+/*
+ * Like chunkcopy_relaxed(), but avoid writing beyond of legal output.
+ *
+ * Unlike chunkcopy_core_safe() above, no guarantee is made regarding the
+ * behaviour of overlapping buffers, regardless of the distance between the
+ * pointers. This is reflected in the `restrict`-qualified pointers, allowing
+ * the compiler to re-order loads and stores.
+ *
+ * Accepts an additional pointer to the end of safe output. A generic safe
+ * copy would use (out + len), but it's normally the case that the end of the
+ * output buffer is beyond the end of the current copy, and this can still be
+ * exploited.
+ */
+static inline unsigned char FAR* chunkcopy_safe(
+ unsigned char FAR* out,
+ const unsigned char FAR* Z_RESTRICT from,
+ unsigned len,
+ unsigned char FAR* limit)
+{
+ Assert(out + len <= limit, "chunk copy exceeds safety limit");
+ return chunkcopy_core_safe(out, from, len, limit);
+}
+
+/*
+ * Perform chunky copy within the same buffer, where the source and destination
+ * may potentially overlap.
+ *
+ * Assumes that len > 0 on entry, and that it's safe to write at least
+ * CHUNKCOPY_CHUNK_SIZE*3 bytes to the output.
+ */
+static inline unsigned char FAR* chunkcopy_lapped_relaxed(
+ unsigned char FAR* out,
+ unsigned dist,
+ unsigned len)
+{
+ if (dist < len && dist < CHUNKCOPY_CHUNK_SIZE) {
+ return chunkset_core(out, dist, len);
+ }
+ return chunkcopy_core(out, out - dist, len);
+}
+
+/*
+ * Behave like chunkcopy_lapped_relaxed(), but avoid writing beyond of legal
+ * output.
+ *
+ * Accepts an additional pointer to the end of safe output. A generic safe
+ * copy would use (out + len), but it's normally the case that the end of the
+ * output buffer is beyond the end of the current copy, and this can still be
+ * exploited.
+ */
+static inline unsigned char FAR* chunkcopy_lapped_safe(
+ unsigned char FAR* out,
+ unsigned dist,
+ unsigned len,
+ unsigned char FAR* limit)
+{
+ Assert(out + len <= limit, "chunk copy exceeds safety limit");
+ if ((limit - out) < (ptrdiff_t) (3 * CHUNKCOPY_CHUNK_SIZE)) {
+ while (len-- > 0) {
+ *out = *(out - dist);
+ out++;
+ }
+ return out;
+ }
+ return chunkcopy_lapped_relaxed(out, dist, len);
+}
+
+
+#undef Z_STATIC_ASSERT
+#undef Z_RESTRICT
+#undef Z_BUILTIN_MEMCPY
+
+#endif //defined(INFLATE_CHUNK_SIMD_NEON)
diff --git a/jdk/src/share/native/java/util/zip/zlib/inflate.c b/jdk/src/share/native/java/util/zip/zlib/inflate.c
index ca904e7..c78e05b 100644
--- a/jdk/src/share/native/java/util/zip/zlib/inflate.c
+++ b/jdk/src/share/native/java/util/zip/zlib/inflate.c
@@ -429,9 +429,16 @@ unsigned copy;
/* if it hasn't been done already, allocate space for the window */
if (state->window == Z_NULL) {
+#if defined(INFLATE_CHUNK_SIMD_NEON)
+ unsigned wsize = 1U << state->wbits;
+ state->window = (unsigned char FAR *)
+ ZALLOC(strm, CHUNKCOPY_CHUNK_SIZE + wsize,
+ sizeof(unsigned char));
+#else
state->window = (unsigned char FAR *)
ZALLOC(strm, 1U << state->wbits,
sizeof(unsigned char));
+#endif
if (state->window == Z_NULL) return 1;
}
diff --git a/jdk/src/share/native/java/util/zip/zlib/zadler32.c b/jdk/src/share/native/java/util/zip/zlib/zadler32.c
index e148022..e024a15 100644
--- a/jdk/src/share/native/java/util/zip/zlib/zadler32.c
+++ b/jdk/src/share/native/java/util/zip/zlib/zadler32.c
@@ -83,7 +83,169 @@ local uLong adler32_combine_ OF((uLong adler1, uLong adler2, z_off64_t len2));
# define MOD63(a) a %= BASE
#endif
-/* ========================================================================= */
+#if defined(ADLER32_SIMD_NEON)
+#include <arm_neon.h>
+/*
+ * Multiply-add bytes by [ 32, 31, 30, ... ] for s2.
+ */
+uint32x4_t ZLIB_INTERNAL mul_add_bytes(
+ uint32x4_t v_s2,
+ uint16x8_t v_column_sum_1,
+ uint16x8_t v_column_sum_2,
+ uint16x8_t v_column_sum_3,
+ uint16x8_t v_column_sum_4)
+{
+ v_s2 = vshlq_n_u32(v_s2, 5);
+
+ v_s2 = vmlal_u16(v_s2, vget_low_u16 (v_column_sum_1),
+ (uint16x4_t) { 32, 31, 30, 29 });
+ v_s2 = vmlal_u16(v_s2, vget_high_u16(v_column_sum_1),
+ (uint16x4_t) { 28, 27, 26, 25 });
+ v_s2 = vmlal_u16(v_s2, vget_low_u16 (v_column_sum_2),
+ (uint16x4_t) { 24, 23, 22, 21 });
+ v_s2 = vmlal_u16(v_s2, vget_high_u16(v_column_sum_2),
+ (uint16x4_t) { 20, 19, 18, 17 });
+ v_s2 = vmlal_u16(v_s2, vget_low_u16 (v_column_sum_3),
+ (uint16x4_t) { 16, 15, 14, 13 });
+ v_s2 = vmlal_u16(v_s2, vget_high_u16(v_column_sum_3),
+ (uint16x4_t) { 12, 11, 10, 9 });
+ v_s2 = vmlal_u16(v_s2, vget_low_u16 (v_column_sum_4),
+ (uint16x4_t) { 8, 7, 6, 5 });
+ v_s2 = vmlal_u16(v_s2, vget_high_u16(v_column_sum_4),
+ (uint16x4_t) { 4, 3, 2, 1 });
+ return v_s2;
+}
+
+/*
+ * Handle leftover data.
+ */
+uLong ZLIB_INTERNAL leftover_handler(uint32_t s1, uint32_t s2, const Bytef *buf, z_size_t len)
+{
+ if (len) {
+ if (len >= 16) {
+ s2 += (s1 += *buf++);
+ s2 += (s1 += *buf++);
+ s2 += (s1 += *buf++);
+ s2 += (s1 += *buf++);
+
+ s2 += (s1 += *buf++);
+ s2 += (s1 += *buf++);
+ s2 += (s1 += *buf++);
+ s2 += (s1 += *buf++);
+
+ s2 += (s1 += *buf++);
+ s2 += (s1 += *buf++);
+ s2 += (s1 += *buf++);
+ s2 += (s1 += *buf++);
+
+ s2 += (s1 += *buf++);
+ s2 += (s1 += *buf++);
+ s2 += (s1 += *buf++);
+ s2 += (s1 += *buf++);
+
+ len -= 16;
+ }
+
+ while (len--) {
+ s2 += (s1 += *buf++);
+ }
+
+ if (s1 >= BASE)
+ s1 -= BASE;
+ s2 %= BASE;
+ }
+
+ /*
+ * Return the recombined sums.
+ */
+ return s1 | (s2 << 16);
+}
+
+uLong ZLIB_INTERNAL adler32_simd_(uLong adler, const Bytef *buf, z_size_t len)
+{
+ /*
+ * Split Adler-32 into component sums.
+ */
+ uint32_t s1 = adler & 0xffff;
+ uint32_t s2 = adler >> 16;
+ /*
+ * Serially compute s1 & s2, until the data is 16-byte aligned.
+ */
+ if ((uintptr_t)buf & 0xf) {
+ while ((uintptr_t)buf & 0xf) {
+ s2 += (s1 += *buf++);
+ --len;
+ }
+ if (s1 >= BASE)
+ s1 -= BASE;
+ s2 %= BASE;
+ }
+ /*
+ * Process the data in blocks.
+ */
+ const unsigned BLOCK_SIZE = 1 << 5;
+ z_size_t blocks = len / BLOCK_SIZE;
+ len -= blocks * BLOCK_SIZE;
+ while (blocks) {
+ unsigned n = NMAX / BLOCK_SIZE; /* The NMAX constraint. */
+ if (n > blocks)
+ n = (unsigned) blocks;
+ blocks -= n;
+ /*
+ * Process n blocks of data. At most NMAX data bytes can be
+ * processed before s2 must be reduced modulo BASE.
+ */
+ uint32x4_t v_s2 = (uint32x4_t) { 0, 0, 0, s1 * n };
+ uint32x4_t v_s1 = (uint32x4_t) { 0, 0, 0, 0 };
+
+ uint16x8_t v_column_sum_1 = vdupq_n_u16(0);
+ uint16x8_t v_column_sum_2 = vdupq_n_u16(0);
+ uint16x8_t v_column_sum_3 = vdupq_n_u16(0);
+ uint16x8_t v_column_sum_4 = vdupq_n_u16(0);
+ do {
+ /*
+ * Load 32 input bytes.
+ */
+ const uint8x16_t bytes1 = vld1q_u8((uint8_t*)(buf));
+ const uint8x16_t bytes2 = vld1q_u8((uint8_t*)(buf + 16));
+ /*
+ * Add previous block byte sum to v_s2.
+ */
+ v_s2 = vaddq_u32(v_s2, v_s1);
+ /*
+ * Horizontally add the bytes for s1.
+ */
+ v_s1 = vpadalq_u16(v_s1, vpadalq_u8(vpaddlq_u8(bytes1), bytes2));
+ /*
+ * Vertically add the bytes for s2.
+ */
+ v_column_sum_1 = vaddw_u8(v_column_sum_1, vget_low_u8 (bytes1));
+ v_column_sum_2 = vaddw_u8(v_column_sum_2, vget_high_u8(bytes1));
+ v_column_sum_3 = vaddw_u8(v_column_sum_3, vget_low_u8 (bytes2));
+ v_column_sum_4 = vaddw_u8(v_column_sum_4, vget_high_u8(bytes2));
+ buf += BLOCK_SIZE;
+ } while (--n);
+ v_s2 = mul_add_bytes(v_s2, v_column_sum_1, v_column_sum_2, v_column_sum_3, v_column_sum_4);
+ /*
+ * Sum epi32 ints v_s1(s2) and accumulate in s1(s2).
+ */
+ uint32x2_t sum1 = vpadd_u32(vget_low_u32(v_s1), vget_high_u32(v_s1));
+ uint32x2_t sum2 = vpadd_u32(vget_low_u32(v_s2), vget_high_u32(v_s2));
+ uint32x2_t s1s2 = vpadd_u32(sum1, sum2);
+
+ s1 += vget_lane_u32(s1s2, 0);
+ s2 += vget_lane_u32(s1s2, 1);
+ /*
+ * Reduce.
+ */
+ s1 %= BASE;
+ s2 %= BASE;
+ }
+ return leftover_handler(s1, s2, buf, len);
+
+}
+#endif
+
uLong ZEXPORT adler32_z(adler, buf, len)
uLong adler;
const Bytef *buf;
@@ -92,6 +254,11 @@ uLong ZEXPORT adler32_z(adler, buf, len)
unsigned long sum2;
unsigned n;
+#if defined(ADLER32_SIMD_NEON)
+ if (buf && len >= 64)
+ return adler32_simd_(adler, buf, len);
+#endif
+
/* split Adler-32 into component sums */
sum2 = (adler >> 16) & 0xffff;
adler &= 0xffff;
diff --git a/jdk/src/share/native/java/util/zip/zlib/zcrc32.c b/jdk/src/share/native/java/util/zip/zlib/zcrc32.c
index c1965fd..ee4e440 100644
--- a/jdk/src/share/native/java/util/zip/zlib/zcrc32.c
+++ b/jdk/src/share/native/java/util/zip/zlib/zcrc32.c
@@ -257,7 +257,56 @@ uLong ZEXPORT crc32_z(crc, buf, len)
return crc ^ 0xffffffffUL;
}
-/* ========================================================================= */
+
+#ifdef CRC32_ARMV8_CRC32
+#include <arm_acle.h>
+
+uLong ZEXPORT crc32(crc, buf, len)
+ uLong crc;
+ const unsigned char FAR *buf;
+ uInt len;
+{
+
+ uint32_t c = (uint32_t) ~crc;
+
+ if (buf == Z_NULL) return 0UL;
+
+ while (len && ((uintptr_t)buf & 7)) {
+ c = __crc32b(c, *buf++);
+ --len;
+ }
+
+ const uint64_t *buf8 = (const uint64_t *)buf;
+
+ while (len >= 64) {
+ c = __crc32d(c, *buf8++);
+ c = __crc32d(c, *buf8++);
+ c = __crc32d(c, *buf8++);
+ c = __crc32d(c, *buf8++);
+
+ c = __crc32d(c, *buf8++);
+ c = __crc32d(c, *buf8++);
+ c = __crc32d(c, *buf8++);
+ c = __crc32d(c, *buf8++);
+ len -= 64;
+ }
+
+ while (len >= 8) {
+ c = __crc32d(c, *buf8++);
+ len -= 8;
+ }
+
+ buf = (const unsigned char *)buf8;
+
+ while (len--) {
+ c = __crc32b(c, *buf++);
+ }
+
+ return ~c;
+}
+
+#else
+
uLong ZEXPORT crc32(crc, buf, len)
uLong crc;
const unsigned char FAR *buf;
@@ -266,6 +315,8 @@ uLong ZEXPORT crc32(crc, buf, len)
return crc32_z(crc, buf, len);
}
+#endif
+
#ifdef BYFOUR
/*