Add feature and bug fix for 8u382
This commit is contained in:
parent
8822d34627
commit
5110184ec9
@ -8,9 +8,7 @@ Subject: Reuse translet in XSLTC for XML
|
||||
hotspot/src/share/vm/runtime/arguments.cpp | 2 +
|
||||
hotspot/src/share/vm/runtime/arguments.hpp | 3 +
|
||||
.../src/share/vm/utilities/accessFlags.hpp | 1 +
|
||||
.../transform/TestXmlTransletEnhance.java | 83 +++++++++++++++++++
|
||||
8 files changed, 144 insertions(+), 3 deletions(-)
|
||||
create mode 100644 jdk/test/javax/xml/jaxp/transform/TestXmlTransletEnhance.java
|
||||
7 files changed, 64 insertions(+), 3 deletions(-)
|
||||
|
||||
diff --git a/hotspot/src/share/vm/classfile/classFileParser.cpp b/hotspot/src/share/vm/classfile/classFileParser.cpp
|
||||
index d8e99e622..b9fde38dc 100644
|
||||
@ -182,95 +180,6 @@ index bc56262d1..b20f0f740 100644
|
||||
void set_has_finalizer() { atomic_set_bits(JVM_ACC_HAS_FINALIZER); }
|
||||
void set_has_final_method() { atomic_set_bits(JVM_ACC_HAS_FINAL_METHOD); }
|
||||
void set_is_cloneable() { atomic_set_bits(JVM_ACC_IS_CLONEABLE); }
|
||||
diff --git a/jdk/test/javax/xml/jaxp/transform/TestXmlTransletEnhance.java b/jdk/test/javax/xml/jaxp/transform/TestXmlTransletEnhance.java
|
||||
new file mode 100644
|
||||
index 000000000..73b848de8
|
||||
--- /dev/null
|
||||
+++ b/jdk/test/javax/xml/jaxp/transform/TestXmlTransletEnhance.java
|
||||
@@ -0,0 +1,83 @@
|
||||
+/*
|
||||
+ * Copyright (c) Huawei Technologies Co., Ltd. 2012-2023. All rights reserved.
|
||||
+ */
|
||||
+
|
||||
+
|
||||
+/* @test
|
||||
+ * @summary a test for xml translet enhance
|
||||
+ * @library /lib/testlibrary
|
||||
+ * @run main TestXmlTransletEnhance
|
||||
+ */
|
||||
+
|
||||
+import javax.xml.transform.TransformerFactory;
|
||||
+import com.sun.org.apache.xalan.internal.xsltc.trax.TransformerFactoryImpl;
|
||||
+import java.lang.reflect.Field;
|
||||
+import static jdk.testlibrary.Asserts.assertEquals;
|
||||
+
|
||||
+public class TestXmlTransletEnhance {
|
||||
+ static final boolean expectedResult = true;
|
||||
+
|
||||
+ public static void main(String[] args) throws InterruptedException {
|
||||
+
|
||||
+ Thread thread = new Mythread("BenchmarkThread xml ");
|
||||
+ thread.start();
|
||||
+ thread.join();
|
||||
+ boolean ret = SharedData.getInstance().getResult();
|
||||
+ assertEquals(ret, expectedResult);
|
||||
+
|
||||
+ }
|
||||
+
|
||||
+ static class Mythread extends Thread {
|
||||
+ Mythread(String name){
|
||||
+ super(name);
|
||||
+ }
|
||||
+
|
||||
+ @Override
|
||||
+ public void run(){
|
||||
+
|
||||
+ try {
|
||||
+
|
||||
+ TransformerFactory tf = TransformerFactory.newInstance();
|
||||
+ TransformerFactoryImpl transformer = new TransformerFactoryImpl();
|
||||
+ Class<?> clazz = transformer.getClass();
|
||||
+
|
||||
+ Field generateTransletFiled = clazz.getDeclaredField("_generateTranslet");
|
||||
+ Field autoTransletFiled = clazz.getDeclaredField("_autoTranslet");
|
||||
+
|
||||
+ generateTransletFiled.setAccessible(true);
|
||||
+ autoTransletFiled.setAccessible(true);
|
||||
+
|
||||
+ boolean value1 = (boolean)generateTransletFiled.get(transformer);
|
||||
+ boolean value2 = (boolean)autoTransletFiled.get(transformer);
|
||||
+
|
||||
+ SharedData.getInstance().setResult(value1 && value2);
|
||||
+
|
||||
+ } catch (NoSuchFieldException| IllegalAccessException | SecurityException | IllegalArgumentException e) {
|
||||
+ e.printStackTrace();
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ static class SharedData {
|
||||
+ private static SharedData instance;
|
||||
+ private boolean result;
|
||||
+
|
||||
+ private SharedData() {
|
||||
+ }
|
||||
+
|
||||
+ public static synchronized SharedData getInstance() {
|
||||
+ if (instance == null) {
|
||||
+ instance = new SharedData();
|
||||
+ }
|
||||
+ return instance;
|
||||
+ }
|
||||
+
|
||||
+ public synchronized boolean getResult() {
|
||||
+ return result;
|
||||
+ }
|
||||
+
|
||||
+ public synchronized void setResult(boolean result) {
|
||||
+ this.result = result;
|
||||
+ }
|
||||
+ }
|
||||
+}
|
||||
--
|
||||
2.22.0
|
||||
|
||||
|
||||
392
8213397-Stack-dump-should-show-more-clearly-when-a-t.patch
Normal file
392
8213397-Stack-dump-should-show-more-clearly-when-a-t.patch
Normal file
@ -0,0 +1,392 @@
|
||||
From 3a774c78473c4fc3dcd1dc39f8c9daec4c5a6502 Mon Sep 17 00:00:00 2001
|
||||
Date: Thu, 21 Sep 2023 14:45:54 +0800
|
||||
Subject: 8213397-Stack-dump-should-show-more-clearly-when-a-t.patch
|
||||
|
||||
---
|
||||
hotspot/src/share/vm/oops/instanceKlass.cpp | 23 +-
|
||||
hotspot/src/share/vm/runtime/thread.cpp | 2 +
|
||||
hotspot/src/share/vm/runtime/thread.hpp | 8 +
|
||||
.../src/share/vm/runtime/thread.inline.hpp | 12 +
|
||||
hotspot/src/share/vm/runtime/vframe.cpp | 8 +
|
||||
.../TestThreadDumpClassInitMonitor.java | 217 ++++++++++++++++++
|
||||
6 files changed, 259 insertions(+), 11 deletions(-)
|
||||
create mode 100644 hotspot/test/runtime/Thread/TestThreadDumpClassInitMonitor.java
|
||||
|
||||
diff --git a/hotspot/src/share/vm/oops/instanceKlass.cpp b/hotspot/src/share/vm/oops/instanceKlass.cpp
|
||||
index 538645bbe..993778270 100644
|
||||
--- a/hotspot/src/share/vm/oops/instanceKlass.cpp
|
||||
+++ b/hotspot/src/share/vm/oops/instanceKlass.cpp
|
||||
@@ -920,25 +920,28 @@ void InstanceKlass::initialize_impl(instanceKlassHandle this_oop, TRAPS) {
|
||||
|
||||
bool wait = false;
|
||||
|
||||
+ assert(THREAD->is_Java_thread(), "non-JavaThread in initialize_impl");
|
||||
+ JavaThread* jt = (JavaThread*)THREAD;
|
||||
+
|
||||
// refer to the JVM book page 47 for description of steps
|
||||
// Step 1
|
||||
{
|
||||
oop init_lock = this_oop->init_lock();
|
||||
ObjectLocker ol(init_lock, THREAD, init_lock != NULL);
|
||||
|
||||
- Thread *self = THREAD; // it's passed the current thread
|
||||
-
|
||||
// Step 2
|
||||
// If we were to use wait() instead of waitInterruptibly() then
|
||||
// we might end up throwing IE from link/symbol resolution sites
|
||||
// that aren't expected to throw. This would wreak havoc. See 6320309.
|
||||
- while(this_oop->is_being_initialized() && !this_oop->is_reentrant_initialization(self)) {
|
||||
- wait = true;
|
||||
- ol.waitUninterruptibly(CHECK);
|
||||
+ while (this_oop->is_being_initialized() && !this_oop->is_reentrant_initialization(jt)) {
|
||||
+ wait = true;
|
||||
+ jt->set_class_to_be_initialized(this_oop());
|
||||
+ ol.waitUninterruptibly(jt);
|
||||
+ jt->set_class_to_be_initialized(NULL);
|
||||
}
|
||||
|
||||
// Step 3
|
||||
- if (this_oop->is_being_initialized() && this_oop->is_reentrant_initialization(self)) {
|
||||
+ if (this_oop->is_being_initialized() && this_oop->is_reentrant_initialization(jt)) {
|
||||
DTRACE_CLASSINIT_PROBE_WAIT(recursive, InstanceKlass::cast(this_oop()), -1,wait);
|
||||
return;
|
||||
}
|
||||
@@ -968,7 +971,7 @@ void InstanceKlass::initialize_impl(instanceKlassHandle this_oop, TRAPS) {
|
||||
|
||||
// Step 6
|
||||
this_oop->set_init_state(being_initialized);
|
||||
- this_oop->set_init_thread(self);
|
||||
+ this_oop->set_init_thread(jt);
|
||||
}
|
||||
|
||||
// Step 7
|
||||
@@ -1004,8 +1007,6 @@ void InstanceKlass::initialize_impl(instanceKlassHandle this_oop, TRAPS) {
|
||||
|
||||
// Step 8
|
||||
{
|
||||
- assert(THREAD->is_Java_thread(), "non-JavaThread in initialize_impl");
|
||||
- JavaThread* jt = (JavaThread*)THREAD;
|
||||
DTRACE_CLASSINIT_PROBE_WAIT(clinit, InstanceKlass::cast(this_oop()), -1,wait);
|
||||
// Timer includes any side effects of class initialization (resolution,
|
||||
// etc), but not recursive entry into call_class_initializer().
|
||||
@@ -1031,14 +1032,14 @@ void InstanceKlass::initialize_impl(instanceKlassHandle this_oop, TRAPS) {
|
||||
CLEAR_PENDING_EXCEPTION;
|
||||
// JVMTI has already reported the pending exception
|
||||
// JVMTI internal flag reset is needed in order to report ExceptionInInitializerError
|
||||
- JvmtiExport::clear_detected_exception((JavaThread*)THREAD);
|
||||
+ JvmtiExport::clear_detected_exception(jt);
|
||||
{
|
||||
EXCEPTION_MARK;
|
||||
this_oop->set_initialization_state_and_notify(initialization_error, THREAD);
|
||||
CLEAR_PENDING_EXCEPTION; // ignore any exception thrown, class initialization error is thrown below
|
||||
// JVMTI has already reported the pending exception
|
||||
// JVMTI internal flag reset is needed in order to report ExceptionInInitializerError
|
||||
- JvmtiExport::clear_detected_exception((JavaThread*)THREAD);
|
||||
+ JvmtiExport::clear_detected_exception(jt);
|
||||
}
|
||||
DTRACE_CLASSINIT_PROBE_WAIT(error, InstanceKlass::cast(this_oop()), -1,wait);
|
||||
if (e->is_a(SystemDictionary::Error_klass())) {
|
||||
diff --git a/hotspot/src/share/vm/runtime/thread.cpp b/hotspot/src/share/vm/runtime/thread.cpp
|
||||
index 2be226463..50543ac73 100644
|
||||
--- a/hotspot/src/share/vm/runtime/thread.cpp
|
||||
+++ b/hotspot/src/share/vm/runtime/thread.cpp
|
||||
@@ -1538,6 +1538,8 @@ void JavaThread::initialize() {
|
||||
_popframe_preserved_args_size = 0;
|
||||
_frames_to_pop_failed_realloc = 0;
|
||||
|
||||
+_class_to_be_initialized = NULL;
|
||||
+
|
||||
pd_initialize();
|
||||
}
|
||||
|
||||
diff --git a/hotspot/src/share/vm/runtime/thread.hpp b/hotspot/src/share/vm/runtime/thread.hpp
|
||||
index 220fe9316..1d3caf9aa 100644
|
||||
--- a/hotspot/src/share/vm/runtime/thread.hpp
|
||||
+++ b/hotspot/src/share/vm/runtime/thread.hpp
|
||||
@@ -1802,11 +1802,19 @@ public:
|
||||
bool is_attaching_via_jni() const { return _jni_attach_state == _attaching_via_jni; }
|
||||
bool has_attached_via_jni() const { return is_attaching_via_jni() || _jni_attach_state == _attached_via_jni; }
|
||||
inline void set_done_attaching_via_jni();
|
||||
+
|
||||
+ // Stack dump assistance: Track the class we want to initialize but for which we have to wait
|
||||
+ // on its init_lock() because it is already being initialized.
|
||||
+ inline void set_class_to_be_initialized(InstanceKlass* k);
|
||||
+ inline InstanceKlass* class_to_be_initialized() const;
|
||||
+
|
||||
private:
|
||||
// This field is used to determine if a thread has claimed
|
||||
// a par_id: it is UINT_MAX if the thread has not claimed a par_id;
|
||||
// otherwise its value is the par_id that has been claimed.
|
||||
uint _claimed_par_id;
|
||||
+
|
||||
+ InstanceKlass* _class_to_be_initialized;
|
||||
public:
|
||||
uint get_claimed_par_id() { return _claimed_par_id; }
|
||||
void set_claimed_par_id(uint id) { _claimed_par_id = id;}
|
||||
diff --git a/hotspot/src/share/vm/runtime/thread.inline.hpp b/hotspot/src/share/vm/runtime/thread.inline.hpp
|
||||
index b05e0ec5c..d3ab3aba9 100644
|
||||
--- a/hotspot/src/share/vm/runtime/thread.inline.hpp
|
||||
+++ b/hotspot/src/share/vm/runtime/thread.inline.hpp
|
||||
@@ -74,4 +74,16 @@ inline void JavaThread::set_done_attaching_via_jni() {
|
||||
OrderAccess::fence();
|
||||
}
|
||||
|
||||
+// Allow tracking of class initialization monitor use
|
||||
+inline void JavaThread::set_class_to_be_initialized(InstanceKlass* k) {
|
||||
+ assert((k == NULL && _class_to_be_initialized != NULL) ||
|
||||
+ (k != NULL && _class_to_be_initialized == NULL), "incorrect usage");
|
||||
+ assert(this == Thread::current(), "Only the current thread can set this field");
|
||||
+ _class_to_be_initialized = k;
|
||||
+}
|
||||
+
|
||||
+inline InstanceKlass* JavaThread::class_to_be_initialized() const {
|
||||
+ return _class_to_be_initialized;
|
||||
+}
|
||||
+
|
||||
#endif // SHARE_VM_RUNTIME_THREAD_INLINE_HPP
|
||||
diff --git a/hotspot/src/share/vm/runtime/vframe.cpp b/hotspot/src/share/vm/runtime/vframe.cpp
|
||||
index b3a6d0770..93d62ade7 100644
|
||||
--- a/hotspot/src/share/vm/runtime/vframe.cpp
|
||||
+++ b/hotspot/src/share/vm/runtime/vframe.cpp
|
||||
@@ -176,6 +176,14 @@ void javaVFrame::print_lock_info_on(outputStream* st, int frame_count) {
|
||||
Klass* k = obj->klass();
|
||||
st->print_cr("\t- %s <" INTPTR_FORMAT "> (a %s)", "parking to wait for ", (address)obj, k->external_name());
|
||||
}
|
||||
+ else if (thread()->osthread()->get_state() == OBJECT_WAIT) {
|
||||
+ // We are waiting on an Object monitor but Object.wait() isn't the
|
||||
+ // top-frame, so we should be waiting on a Class initialization monitor.
|
||||
+ InstanceKlass* k = thread()->class_to_be_initialized();
|
||||
+ if (k != NULL) {
|
||||
+ st->print_cr("\t- waiting on the Class initialization monitor for %s", k->external_name());
|
||||
+ }
|
||||
+ }
|
||||
}
|
||||
|
||||
|
||||
diff --git a/hotspot/test/runtime/Thread/TestThreadDumpClassInitMonitor.java b/hotspot/test/runtime/Thread/TestThreadDumpClassInitMonitor.java
|
||||
new file mode 100644
|
||||
index 000000000..8aa218efb
|
||||
--- /dev/null
|
||||
+++ b/hotspot/test/runtime/Thread/TestThreadDumpClassInitMonitor.java
|
||||
@@ -0,0 +1,217 @@
|
||||
+/*
|
||||
+ * Copyright (c) 2019, Oracle and/or its affiliates. All rights reserved.
|
||||
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
+ *
|
||||
+ * This code is free software; you can redistribute it and/or modify it
|
||||
+ * under the terms of the GNU General Public License version 2 only, as
|
||||
+ * published by the Free Software Foundation.
|
||||
+ *
|
||||
+ * This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
+ * version 2 for more details (a copy is included in the LICENSE file that
|
||||
+ * accompanied this code).
|
||||
+ *
|
||||
+ * You should have received a copy of the GNU General Public License version
|
||||
+ * 2 along with this work; if not, write to the Free Software Foundation,
|
||||
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
+ *
|
||||
+ * Please 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 8213397 8217337
|
||||
+ * @summary Check that the thread dump shows when a thread is blocked
|
||||
+ * on a class initialization monitor
|
||||
+ *
|
||||
+ * @library /testlibrary
|
||||
+ * @run main/othervm TestThreadDumpClassInitMonitor
|
||||
+ */
|
||||
+
|
||||
+import com.oracle.java.testlibrary.*;
|
||||
+
|
||||
+import java.io.IOException;
|
||||
+import java.util.List;
|
||||
+import java.lang.management.ManagementFactory;
|
||||
+import java.lang.management.RuntimeMXBean;
|
||||
+
|
||||
+public class TestThreadDumpClassInitMonitor {
|
||||
+ // jstack tends to be closely bound to the VM that we are running
|
||||
+ // so use getTestJDKTool() instead of getCompileJDKTool() or even
|
||||
+ // getJDKTool() which can fall back to "compile.jdk".
|
||||
+ final static String JSTACK = JDKToolFinder.getTestJDKTool("jstack");
|
||||
+ final static String PID = getPid();
|
||||
+ final static Thread current = Thread.currentThread();
|
||||
+
|
||||
+ /*
|
||||
+ * This is the output we're looking for:
|
||||
+ *
|
||||
+ * "TestThread" #22 prio=5 os_prio=0 cpu=1.19ms elapsed=0.80s tid=0x00007f8f9405d800 nid=0x568b in Object.wait() [0x00007f8fd94d0000]
|
||||
+ * java.lang.Thread.State: RUNNABLE
|
||||
+ * Thread: 0x00007f8f9405d800 [0x568b] State: _at_safepoint _has_called_back 0 _at_poll_safepoint 0 // DEBUG ONLY
|
||||
+ * JavaThread state: _thread_blocked // DEBUG ONLY
|
||||
+ * at TestThreadDumpClassInitMonitor$Target$1.run(TestThreadDumpClassInitMonitor.java:69)
|
||||
+ * - waiting on the Class initialization monitor for TestThreadDumpClassInitMonitor$Target
|
||||
+ *
|
||||
+ */
|
||||
+ final static String TEST_THREAD = "TestThread";
|
||||
+ final static String TEST_THREAD_ENTRY = "\"" + TEST_THREAD;
|
||||
+ final static String IN_OBJECT_WAIT = "in Object.wait()";
|
||||
+ final static String THREAD_STATE = "java.lang.Thread.State: RUNNABLE";
|
||||
+ final static String THREAD_INFO = "Thread:"; // the details are not important
|
||||
+ final static String JAVATHREAD_STATE = "JavaThread state: _thread_blocked";
|
||||
+ final static String CURRENT_METHOD = "at TestThreadDumpClassInitMonitor$Target$1.run";
|
||||
+ final static String WAIT_INFO = "- waiting on the Class initialization monitor for TestThreadDumpClassInitMonitor$Target";
|
||||
+
|
||||
+ volatile static boolean ready = false;
|
||||
+
|
||||
+ static List<String> stackDump; // jstack output as lines
|
||||
+
|
||||
+ static class Target {
|
||||
+
|
||||
+ static int field;
|
||||
+
|
||||
+ // The main thread will initialize this class and so
|
||||
+ // execute the actual test logic here.
|
||||
+ static {
|
||||
+ if (Thread.currentThread() != current) {
|
||||
+ throw new Error("Initialization logic error");
|
||||
+ }
|
||||
+ System.out.println("Initializing Target class in main thread");
|
||||
+
|
||||
+ Thread t = new Thread() {
|
||||
+ public void run() {
|
||||
+ System.out.println("Test thread about to access Target");
|
||||
+ ready = true; // tell main thread we're close
|
||||
+ // This will block until the main thread completes
|
||||
+ // static initialization of target
|
||||
+ Target.field = 42;
|
||||
+ System.out.println("Test thread done");
|
||||
+ }
|
||||
+ };
|
||||
+ t.setName(TEST_THREAD);
|
||||
+ t.start();
|
||||
+
|
||||
+ // We want to run jstack once the test thread is blocked but
|
||||
+ // there's no programmatic way to detect that. So we check the flag
|
||||
+ // that will be set just before it should block, then by the time
|
||||
+ // we can exec jstack it should be ready.
|
||||
+ try {
|
||||
+ while (!ready) {
|
||||
+ Thread.sleep(200);
|
||||
+ }
|
||||
+ }
|
||||
+ catch (InterruptedException ie) {
|
||||
+ throw new Error("Shouldn't happen");
|
||||
+ }
|
||||
+
|
||||
+ // Now run jstack
|
||||
+ try {
|
||||
+ ProcessBuilder pb = new ProcessBuilder(JSTACK, PID);
|
||||
+ OutputAnalyzer output = new OutputAnalyzer(pb.start());
|
||||
+ output.shouldHaveExitValue(0);
|
||||
+ stackDump = output.asLines();
|
||||
+ }
|
||||
+ catch (IOException ioe) {
|
||||
+ throw new Error("Launching jstack failed", ioe);
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+
|
||||
+ public static void main(String[] args) throws Throwable {
|
||||
+ // Implicitly run the main test logic
|
||||
+ Target.field = 21;
|
||||
+
|
||||
+ // Now check the output of jstack
|
||||
+ try {
|
||||
+ // product builds miss 2 lines of information in the stack
|
||||
+ boolean isProduct = !Platform.isDebugBuild();
|
||||
+ int foundLines = 0;
|
||||
+ parseStack: for (String line : stackDump) {
|
||||
+ switch(foundLines) {
|
||||
+ case 0: {
|
||||
+ if (!line.startsWith(TEST_THREAD_ENTRY)) {
|
||||
+ continue;
|
||||
+ }
|
||||
+ foundLines++;
|
||||
+ if (!line.contains(IN_OBJECT_WAIT)) {
|
||||
+ throw new Error("Unexpected initial stack line: " + line);
|
||||
+ }
|
||||
+ continue;
|
||||
+ }
|
||||
+ case 1: {
|
||||
+ if (!line.trim().equals(THREAD_STATE)) {
|
||||
+ throw new Error("Unexpected thread state line: " + line);
|
||||
+ }
|
||||
+ if (isProduct) {
|
||||
+ foundLines += 3;
|
||||
+ } else {
|
||||
+ foundLines++;
|
||||
+ }
|
||||
+ continue;
|
||||
+ }
|
||||
+ case 2: { // Debug build
|
||||
+ if (!line.startsWith(THREAD_INFO)) {
|
||||
+ throw new Error("Unexpected thread info line: " + line);
|
||||
+ }
|
||||
+ foundLines++;
|
||||
+ continue;
|
||||
+ }
|
||||
+ case 3: { // Debug build
|
||||
+ if (!line.trim().equals(JAVATHREAD_STATE)) {
|
||||
+ throw new Error("Unexpected JavaThread state line: " + line);
|
||||
+ }
|
||||
+ foundLines++;
|
||||
+ continue;
|
||||
+ }
|
||||
+ case 4: {
|
||||
+ if (!line.trim().startsWith(CURRENT_METHOD)) {
|
||||
+ throw new Error("Unexpected current method line: " + line);
|
||||
+ }
|
||||
+ foundLines++;
|
||||
+ continue;
|
||||
+ }
|
||||
+ case 5: {
|
||||
+ if (!line.trim().equals(WAIT_INFO)) {
|
||||
+ throw new Error("Unexpected monitor information line: " + line);
|
||||
+ }
|
||||
+ break parseStack;
|
||||
+ }
|
||||
+ default: throw new Error("Logic error in case statement");
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ if (foundLines == 0) {
|
||||
+ throw new Error("Unexpected stack content - did not find line starting with "
|
||||
+ + TEST_THREAD_ENTRY);
|
||||
+ }
|
||||
+ }
|
||||
+ catch (Error e) {
|
||||
+ // Dump the full stack trace on error so we can check the content
|
||||
+ for (String line : stackDump) {
|
||||
+ System.out.println(line);
|
||||
+ }
|
||||
+ throw e;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ // This helper relies on RuntimeMXBean.getName() returning a string
|
||||
+ // that looks like this: 5436@mt-haku
|
||||
+ //
|
||||
+ // The testlibrary has tryFindJvmPid(), but that uses a separate
|
||||
+ // process which is much more expensive for finding out your own PID.
|
||||
+ //
|
||||
+ static String getPid() {
|
||||
+ RuntimeMXBean runtimebean = ManagementFactory.getRuntimeMXBean();
|
||||
+ String vmname = runtimebean.getName();
|
||||
+ int i = vmname.indexOf('@');
|
||||
+ if (i != -1) {
|
||||
+ vmname = vmname.substring(0, i);
|
||||
+ }
|
||||
+ return vmname;
|
||||
+ }
|
||||
+}
|
||||
\ No newline at end of file
|
||||
--
|
||||
2.22.0
|
||||
|
||||
277
8254723-Add-diagnostic-command-to-write-Linux-perf-m.patch
Normal file
277
8254723-Add-diagnostic-command-to-write-Linux-perf-m.patch
Normal file
@ -0,0 +1,277 @@
|
||||
From 6a5759c82b869c4d931273609aa19eb1a84df8db Mon Sep 17 00:00:00 2001
|
||||
Date: Thu, 21 Sep 2023 15:12:51 +0800
|
||||
Subject: 8254723-Add-diagnostic-command-to-write-Linux-perf-m.patch
|
||||
|
||||
---
|
||||
hotspot/src/os/linux/vm/globals_linux.hpp | 5 +-
|
||||
hotspot/src/os/linux/vm/os_linux.cpp | 6 ++
|
||||
hotspot/src/share/vm/code/codeCache.cpp | 36 ++++++++
|
||||
hotspot/src/share/vm/code/codeCache.hpp | 1 +
|
||||
hotspot/src/share/vm/runtime/java.cpp | 6 ++
|
||||
.../share/vm/services/diagnosticCommand.cpp | 7 ++
|
||||
.../share/vm/services/diagnosticCommand.hpp | 23 +++++
|
||||
.../test/serviceability/dcmd/PerfMapTest.java | 84 +++++++++++++++++++
|
||||
8 files changed, 167 insertions(+), 1 deletion(-)
|
||||
create mode 100644 hotspot/test/serviceability/dcmd/PerfMapTest.java
|
||||
|
||||
diff --git a/hotspot/src/os/linux/vm/globals_linux.hpp b/hotspot/src/os/linux/vm/globals_linux.hpp
|
||||
index f98bde41a..5cbe686d3 100644
|
||||
--- a/hotspot/src/os/linux/vm/globals_linux.hpp
|
||||
+++ b/hotspot/src/os/linux/vm/globals_linux.hpp
|
||||
@@ -55,7 +55,10 @@
|
||||
product(bool, PreferContainerQuotaForCPUCount, true, \
|
||||
"Calculate the container CPU availability based on the value" \
|
||||
" of quotas (if set), when true. Otherwise, use the CPU" \
|
||||
- " shares value, provided it is less than quota.")
|
||||
+ " shares value, provided it is less than quota.") \
|
||||
+ \
|
||||
+ diagnostic(bool, DumpPerfMapAtExit, false, \
|
||||
+ "Write map file for Linux perf tool at exit")
|
||||
|
||||
//
|
||||
// Defines Linux-specific default values. The flags are available on all
|
||||
diff --git a/hotspot/src/os/linux/vm/os_linux.cpp b/hotspot/src/os/linux/vm/os_linux.cpp
|
||||
index a1cc85ca3..197b5c193 100644
|
||||
--- a/hotspot/src/os/linux/vm/os_linux.cpp
|
||||
+++ b/hotspot/src/os/linux/vm/os_linux.cpp
|
||||
@@ -5648,6 +5648,12 @@ jint os::init_2(void)
|
||||
// initialize thread priority policy
|
||||
prio_init();
|
||||
|
||||
+ if (DumpPerfMapAtExit && FLAG_IS_DEFAULT(UseCodeCacheFlushing)) {
|
||||
+ // Disable code cache flushing to ensure the map file written at
|
||||
+ // exit contains all nmethods generated during execution.
|
||||
+ FLAG_SET_DEFAULT(UseCodeCacheFlushing, false);
|
||||
+ }
|
||||
+
|
||||
return JNI_OK;
|
||||
}
|
||||
|
||||
diff --git a/hotspot/src/share/vm/code/codeCache.cpp b/hotspot/src/share/vm/code/codeCache.cpp
|
||||
index 37f24b5e9..97ad3ba79 100644
|
||||
--- a/hotspot/src/share/vm/code/codeCache.cpp
|
||||
+++ b/hotspot/src/share/vm/code/codeCache.cpp
|
||||
@@ -1033,3 +1033,39 @@ void CodeCache::log_state(outputStream* st) {
|
||||
unallocated_capacity());
|
||||
}
|
||||
|
||||
+#ifdef LINUX
|
||||
+void CodeCache::write_perf_map() {
|
||||
+ MutexLockerEx mu(CodeCache_lock, Mutex::_no_safepoint_check_flag);
|
||||
+
|
||||
+ // Perf expects to find the map file at /tmp/perf-<pid>.map.
|
||||
+ char fname[32];
|
||||
+ jio_snprintf(fname, sizeof(fname), "/tmp/perf-%d.map", os::current_process_id());
|
||||
+
|
||||
+ fileStream fs(fname, "w");
|
||||
+ if (!fs.is_open()) {
|
||||
+ DEBUG_ONLY(warning("[codecache] Failed to create %s for perf map", fname));
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
+ FOR_ALL_ALIVE_BLOBS(cb) {
|
||||
+ if (cb->is_nmethod()) {
|
||||
+ nmethod *nm = (nmethod *) cb;
|
||||
+ assert(!nm->is_unloaded(), "Tautology");
|
||||
+ ResourceMark rm;
|
||||
+ const char* method_name = nm->method()->name_and_sig_as_C_string();
|
||||
+ fs.print_cr(INTPTR_FORMAT " " INTPTR_FORMAT " %s",
|
||||
+ (intptr_t)cb->code_begin(), (intptr_t)cb->code_size(),
|
||||
+ method_name);
|
||||
+ }
|
||||
+ if (cb->is_runtime_stub()) {
|
||||
+ RuntimeStub *stub = (RuntimeStub *) cb;
|
||||
+ ResourceMark rm;
|
||||
+ const char* method_name = stub->name();
|
||||
+ fs.print_cr(INTPTR_FORMAT " " INTPTR_FORMAT " %s",
|
||||
+ (intptr_t)cb->code_begin(), (intptr_t)cb->code_size(),
|
||||
+ method_name);
|
||||
+ }
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
+#endif // LINUX
|
||||
diff --git a/hotspot/src/share/vm/code/codeCache.hpp b/hotspot/src/share/vm/code/codeCache.hpp
|
||||
index ab1417b19..0aad2d648 100644
|
||||
--- a/hotspot/src/share/vm/code/codeCache.hpp
|
||||
+++ b/hotspot/src/share/vm/code/codeCache.hpp
|
||||
@@ -158,6 +158,7 @@ class CodeCache : AllStatic {
|
||||
static void print_trace(const char* event, CodeBlob* cb, int size = 0) PRODUCT_RETURN;
|
||||
static void print_summary(outputStream* st, bool detailed = true); // Prints a summary of the code cache usage
|
||||
static void log_state(outputStream* st);
|
||||
+ LINUX_ONLY(static void write_perf_map();)
|
||||
|
||||
// Dcmd (Diagnostic commands)
|
||||
static void print_codelist(outputStream* st);
|
||||
diff --git a/hotspot/src/share/vm/runtime/java.cpp b/hotspot/src/share/vm/runtime/java.cpp
|
||||
index 5a628b73e..fec8fb94d 100644
|
||||
--- a/hotspot/src/share/vm/runtime/java.cpp
|
||||
+++ b/hotspot/src/share/vm/runtime/java.cpp
|
||||
@@ -537,6 +537,12 @@ void before_exit(JavaThread * thread) {
|
||||
BytecodeHistogram::print();
|
||||
}
|
||||
|
||||
+#ifdef LINUX
|
||||
+ if (DumpPerfMapAtExit) {
|
||||
+ CodeCache::write_perf_map();
|
||||
+ }
|
||||
+#endif
|
||||
+
|
||||
if (JvmtiExport::should_post_thread_life()) {
|
||||
JvmtiExport::post_thread_end(thread);
|
||||
}
|
||||
diff --git a/hotspot/src/share/vm/services/diagnosticCommand.cpp b/hotspot/src/share/vm/services/diagnosticCommand.cpp
|
||||
index 416dc77ce..f8f6ad546 100644
|
||||
--- a/hotspot/src/share/vm/services/diagnosticCommand.cpp
|
||||
+++ b/hotspot/src/share/vm/services/diagnosticCommand.cpp
|
||||
@@ -36,6 +36,7 @@
|
||||
#include "services/management.hpp"
|
||||
#include "utilities/macros.hpp"
|
||||
#include "oops/objArrayOop.hpp"
|
||||
+#include "code/codeCache.hpp"
|
||||
|
||||
#ifdef LINUX
|
||||
#include "trimCHeapDCmd.hpp"
|
||||
@@ -81,6 +82,7 @@ void DCmdRegistrant::register_dcmds(){
|
||||
#ifdef LINUX
|
||||
DCmdFactory::register_DCmdFactory(new DCmdFactoryImpl<TrimCLibcHeapDCmd>(full_export, true, false));
|
||||
DCmdFactory::register_DCmdFactory(new DCmdFactoryImpl<MallocInfoDcmd>(full_export, true, false));
|
||||
+ DCmdFactory::register_DCmdFactory(new DCmdFactoryImpl<PerfMapDCmd>(full_export, true, false));
|
||||
#endif // LINUX
|
||||
|
||||
// Enhanced JMX Agent Support
|
||||
@@ -868,3 +870,8 @@ void CodeCacheDCmd::execute(DCmdSource source, TRAPS) {
|
||||
VMThread::execute(&printCodeCacheOp);
|
||||
}
|
||||
|
||||
+#ifdef LINUX
|
||||
+void PerfMapDCmd::execute(DCmdSource source, TRAPS) {
|
||||
+ CodeCache::write_perf_map();
|
||||
+}
|
||||
+#endif // LINUX
|
||||
\ No newline at end of file
|
||||
diff --git a/hotspot/src/share/vm/services/diagnosticCommand.hpp b/hotspot/src/share/vm/services/diagnosticCommand.hpp
|
||||
index 3733fa7f7..d446aab4e 100644
|
||||
--- a/hotspot/src/share/vm/services/diagnosticCommand.hpp
|
||||
+++ b/hotspot/src/share/vm/services/diagnosticCommand.hpp
|
||||
@@ -590,4 +590,27 @@ public:
|
||||
virtual void execute(DCmdSource source, TRAPS);
|
||||
};
|
||||
|
||||
+#ifdef LINUX
|
||||
+class PerfMapDCmd : public DCmd {
|
||||
+public:
|
||||
+ PerfMapDCmd(outputStream* output, bool heap) : DCmd(output, heap) {}
|
||||
+ static const char* name() {
|
||||
+ return "Compiler.perfmap";
|
||||
+ }
|
||||
+ static const char* description() {
|
||||
+ return "Write map file for Linux perf tool.";
|
||||
+ }
|
||||
+ static const char* impact() {
|
||||
+ return "Low";
|
||||
+ }
|
||||
+ static const JavaPermission permission() {
|
||||
+ JavaPermission p = {"java.lang.management.ManagementPermission",
|
||||
+ "monitor", NULL};
|
||||
+ return p;
|
||||
+ }
|
||||
+ static int num_arguments() { return 0; }
|
||||
+ virtual void execute(DCmdSource source, TRAPS);
|
||||
+};
|
||||
+#endif // LINUX
|
||||
+
|
||||
#endif // SHARE_VM_SERVICES_DIAGNOSTICCOMMAND_HPP
|
||||
diff --git a/hotspot/test/serviceability/dcmd/PerfMapTest.java b/hotspot/test/serviceability/dcmd/PerfMapTest.java
|
||||
new file mode 100644
|
||||
index 000000000..1807b2a7f
|
||||
--- /dev/null
|
||||
+++ b/hotspot/test/serviceability/dcmd/PerfMapTest.java
|
||||
@@ -0,0 +1,84 @@
|
||||
+/*
|
||||
+ * Copyright (c) 2020, Oracle and/or its affiliates. All rights reserved.
|
||||
+ * Copyright (c) 2020, Arm Limited. All rights reserved.
|
||||
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
+ *
|
||||
+ * This code is free software; you can redistribute it and/or modify it
|
||||
+ * under the terms of the GNU General Public License version 2 only, as
|
||||
+ * published by the Free Software Foundation.
|
||||
+ *
|
||||
+ * This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
+ * version 2 for more details (a copy is included in the LICENSE file that
|
||||
+ * accompanied this code).
|
||||
+ *
|
||||
+ * You should have received a copy of the GNU General Public License version
|
||||
+ * 2 along with this work; if not, write to the Free Software Foundation,
|
||||
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
+ *
|
||||
+ * Please 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 PerfMapTest
|
||||
+ * @bug 8254723
|
||||
+ * @requires os.family == "linux"
|
||||
+ * @library /testlibrary
|
||||
+ * @run testng/othervm PerfMapTest
|
||||
+ * @summary Test of diagnostic command Compiler.perfmap
|
||||
+ */
|
||||
+
|
||||
+import org.testng.annotations.Test;
|
||||
+import org.testng.Assert;
|
||||
+
|
||||
+import com.oracle.java.testlibrary.OutputAnalyzer;
|
||||
+import com.oracle.java.testlibrary.CommandExecutor;
|
||||
+import com.oracle.java.testlibrary.JMXExecutor;
|
||||
+import com.oracle.java.testlibrary.ProcessTools;
|
||||
+
|
||||
+import java.io.IOException;
|
||||
+import java.nio.file.Files;
|
||||
+import java.nio.file.Path;
|
||||
+import java.nio.file.Paths;
|
||||
+import java.util.regex.Matcher;
|
||||
+import java.util.regex.Pattern;
|
||||
+
|
||||
+/**
|
||||
+ * Call jcmd Compiler.perfmap and check the output file has the expected
|
||||
+ * format.
|
||||
+ */
|
||||
+public class PerfMapTest {
|
||||
+
|
||||
+ static final Pattern LINE_PATTERN =
|
||||
+ Pattern.compile("^((?:0x)?\\p{XDigit}+)\\s+((?:0x)?\\p{XDigit}+)\\s+(.*)$");
|
||||
+
|
||||
+ public void run(CommandExecutor executor) throws Exception {
|
||||
+ OutputAnalyzer output = executor.execute("Compiler.perfmap");
|
||||
+
|
||||
+ output.stderrShouldBeEmpty();
|
||||
+ output.stdoutShouldBeEmpty();
|
||||
+
|
||||
+ final long pid = ProcessTools.getProcessId();
|
||||
+ final Path path = Paths.get(String.format("/tmp/perf-%d.map", pid));
|
||||
+
|
||||
+ Assert.assertTrue(Files.exists(path));
|
||||
+
|
||||
+ // Sanity check the file contents
|
||||
+ try {
|
||||
+ for (String entry : Files.readAllLines(path)) {
|
||||
+ Matcher m = LINE_PATTERN.matcher(entry);
|
||||
+ Assert.assertTrue(m.matches(), "Invalid file format: " + entry);
|
||||
+ }
|
||||
+ } catch (IOException e) {
|
||||
+ Assert.fail(e.toString());
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ @Test
|
||||
+ public void jmx() throws Exception {
|
||||
+ run(new JMXExecutor());
|
||||
+ }
|
||||
+}
|
||||
--
|
||||
2.22.0
|
||||
|
||||
25
8295068-SSLEngine-throws-NPE-parsing-CertificateRequ.patch
Normal file
25
8295068-SSLEngine-throws-NPE-parsing-CertificateRequ.patch
Normal file
@ -0,0 +1,25 @@
|
||||
From 559bf67072bcf7fe854d03aebdfb49e02bd75899 Mon Sep 17 00:00:00 2001
|
||||
From: DXwangg <wangjiawei80@huawei.com>
|
||||
Date: Mon, 25 Sep 2023 09:50:38 +0800
|
||||
Subject: [PATCH] 8295068: SSLEngine throws NPE parsing CertificateRequests
|
||||
|
||||
---
|
||||
jdk/src/share/classes/sun/security/ssl/CertificateRequest.java | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/jdk/src/share/classes/sun/security/ssl/CertificateRequest.java b/jdk/src/share/classes/sun/security/ssl/CertificateRequest.java
|
||||
index 475ec42c..ad0325e4 100644
|
||||
--- a/jdk/src/share/classes/sun/security/ssl/CertificateRequest.java
|
||||
+++ b/jdk/src/share/classes/sun/security/ssl/CertificateRequest.java
|
||||
@@ -135,7 +135,7 @@ final class CertificateRequest {
|
||||
ArrayList<String> keyTypes = new ArrayList<>(3);
|
||||
for (byte id : ids) {
|
||||
ClientCertificateType cct = ClientCertificateType.valueOf(id);
|
||||
- if (cct.isAvailable) {
|
||||
+ if (cct != null && cct.isAvailable) {
|
||||
keyTypes.add(cct.keyAlgorithm);
|
||||
}
|
||||
}
|
||||
--
|
||||
2.39.0
|
||||
|
||||
66
Record-the-number-of-processes-to-errlog-file.patch.patch
Normal file
66
Record-the-number-of-processes-to-errlog-file.patch.patch
Normal file
@ -0,0 +1,66 @@
|
||||
From 752494be2626cb819c92269e26f53833b2538160 Mon Sep 17 00:00:00 2001
|
||||
Date: Thu, 21 Sep 2023 14:46:56 +0800
|
||||
Subject: Record-the-number-of-processes-to-errlog-file.patch
|
||||
|
||||
---
|
||||
hotspot/src/os/linux/vm/os_linux.cpp | 24 ++++++++++++++++++++++++
|
||||
hotspot/src/os/linux/vm/os_linux.hpp | 1 +
|
||||
2 files changed, 25 insertions(+)
|
||||
|
||||
diff --git a/hotspot/src/os/linux/vm/os_linux.cpp b/hotspot/src/os/linux/vm/os_linux.cpp
|
||||
index 72839eb5a..a1cc85ca3 100644
|
||||
--- a/hotspot/src/os/linux/vm/os_linux.cpp
|
||||
+++ b/hotspot/src/os/linux/vm/os_linux.cpp
|
||||
@@ -2256,6 +2256,10 @@ void os::print_os_info(outputStream* st) {
|
||||
|
||||
os::Posix::print_load_average(st);
|
||||
|
||||
+ if (ExtensiveErrorReports) {
|
||||
+ os::Linux::print_system_process_count(st);
|
||||
+ }
|
||||
+
|
||||
os::Linux::print_system_memory_info(st);
|
||||
st->cr();
|
||||
|
||||
@@ -2323,6 +2327,26 @@ void os::Linux::print_libversion_info(outputStream* st) {
|
||||
st->cr();
|
||||
}
|
||||
|
||||
+void os::Linux::print_system_process_count(outputStream* st) {
|
||||
+ // system process count
|
||||
+ DIR *dir = opendir("/proc");
|
||||
+ if (dir == NULL) {
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
+ st->print("system process count:");
|
||||
+ uint count = 0;
|
||||
+ struct dirent *ptr;
|
||||
+ while ((ptr = readdir(dir)) != NULL) {
|
||||
+ if(ptr->d_type == DT_DIR && isdigit((ptr->d_name)[0])) {
|
||||
+ count++;
|
||||
+ }
|
||||
+ }
|
||||
+ (void) closedir(dir);
|
||||
+ st->print("%u", count);
|
||||
+ st->cr();
|
||||
+}
|
||||
+
|
||||
void os::Linux::print_system_memory_info(outputStream* st) {
|
||||
st->print("\n/proc/meminfo:\n");
|
||||
_print_ascii_file("/proc/meminfo", st);
|
||||
diff --git a/hotspot/src/os/linux/vm/os_linux.hpp b/hotspot/src/os/linux/vm/os_linux.hpp
|
||||
index a516335d2..19dde2e58 100644
|
||||
--- a/hotspot/src/os/linux/vm/os_linux.hpp
|
||||
+++ b/hotspot/src/os/linux/vm/os_linux.hpp
|
||||
@@ -124,6 +124,7 @@ class Linux {
|
||||
static void print_container_info(outputStream* st);
|
||||
static void print_distro_info(outputStream* st);
|
||||
static void print_libversion_info(outputStream* st);
|
||||
+ static void print_system_process_count(outputStream* st);
|
||||
static void print_proc_sys_info(outputStream* st);
|
||||
|
||||
public:
|
||||
--
|
||||
2.22.0
|
||||
|
||||
89
The-OverWriteOldestGCLog-option-is-added-to-control.patch
Normal file
89
The-OverWriteOldestGCLog-option-is-added-to-control.patch
Normal file
@ -0,0 +1,89 @@
|
||||
From 2fd15967a7974d1d61cc7aa706c82733c572964d Mon Sep 17 00:00:00 2001
|
||||
Date: Thu, 21 Sep 2023 15:14:11 +0800
|
||||
Subject: The-OverWriteOldestGCLog-option-is-added-to-control
|
||||
|
||||
---
|
||||
hotspot/src/share/vm/runtime/globals.hpp | 3 ++
|
||||
hotspot/src/share/vm/utilities/ostream.cpp | 45 ++++++++++++++++++++++
|
||||
2 files changed, 48 insertions(+)
|
||||
|
||||
diff --git a/hotspot/src/share/vm/runtime/globals.hpp b/hotspot/src/share/vm/runtime/globals.hpp
|
||||
index 4f649bd45..fdd9db149 100644
|
||||
--- a/hotspot/src/share/vm/runtime/globals.hpp
|
||||
+++ b/hotspot/src/share/vm/runtime/globals.hpp
|
||||
@@ -2571,6 +2571,9 @@ class CommandLineFlags {
|
||||
"GC log file size, requires UseGCLogFileRotation. " \
|
||||
"Set to 0 to only trigger rotation via jcmd") \
|
||||
\
|
||||
+ product(bool, OverWriteOldestGCLog, false, \
|
||||
+ "Over write the oldest gclog") \
|
||||
+ \
|
||||
/* JVMTI heap profiling */ \
|
||||
\
|
||||
diagnostic(bool, TraceJVMTIObjectTagging, false, \
|
||||
diff --git a/hotspot/src/share/vm/utilities/ostream.cpp b/hotspot/src/share/vm/utilities/ostream.cpp
|
||||
index f4e127145..133b5a7c0 100644
|
||||
--- a/hotspot/src/share/vm/utilities/ostream.cpp
|
||||
+++ b/hotspot/src/share/vm/utilities/ostream.cpp
|
||||
@@ -843,6 +843,48 @@ gcLogFileStream::~gcLogFileStream() {
|
||||
delete _file_lock;
|
||||
}
|
||||
|
||||
+static uintx next_file_number(const char* filename) {
|
||||
+ uintx next_num;
|
||||
+ uintx index;
|
||||
+ char gclog[JVM_MAXPATHLEN];
|
||||
+ struct stat st;
|
||||
+ long oldestTime = LONG_MAX;
|
||||
+ bool normal_file_exist;
|
||||
+ bool current_file_exist;
|
||||
+ for (index = 0; index < NumberOfGCLogFiles; ++index) {
|
||||
+ // normal gc log file
|
||||
+ jio_snprintf(gclog, JVM_MAXPATHLEN, "%s.%d", filename, index);
|
||||
+ normal_file_exist = (os::stat(gclog, &st) == 0);
|
||||
+ if (normal_file_exist && oldestTime > st.st_mtime) {
|
||||
+ oldestTime = st.st_mtime;
|
||||
+ next_num = index;
|
||||
+ }
|
||||
+
|
||||
+ // current gc log file
|
||||
+ jio_snprintf(gclog, JVM_MAXPATHLEN, "%s.%d" CURRENTAPPX, filename, index);
|
||||
+ current_file_exist = (os::stat(gclog, &st) == 0);
|
||||
+ if (current_file_exist && oldestTime > st.st_mtime) {
|
||||
+ oldestTime = st.st_mtime;
|
||||
+ next_num = index;
|
||||
+ }
|
||||
+
|
||||
+ // Stop looking if we find an unused file name
|
||||
+ if (!normal_file_exist && !current_file_exist) {
|
||||
+ next_num = index;
|
||||
+ break;
|
||||
+ }
|
||||
+ }
|
||||
+ // remove the existing normal file
|
||||
+ char exist_file_name[JVM_MAXPATHLEN];
|
||||
+ jio_snprintf(exist_file_name, JVM_MAXPATHLEN, "%s.%d", filename, next_num);
|
||||
+ if (access(exist_file_name, F_OK) == 0) {
|
||||
+ if (remove(exist_file_name) != 0) {
|
||||
+ warning("Could not delete existing normal file %s\n", exist_file_name);
|
||||
+ }
|
||||
+ }
|
||||
+ return next_num;
|
||||
+}
|
||||
+
|
||||
gcLogFileStream::gcLogFileStream(const char* file_name) : _file_lock(NULL) {
|
||||
_cur_file_num = 0;
|
||||
_bytes_written = 0L;
|
||||
@@ -857,6 +899,9 @@ gcLogFileStream::gcLogFileStream(const char* file_name) : _file_lock(NULL) {
|
||||
|
||||
// gc log file rotation
|
||||
if (UseGCLogFileRotation && NumberOfGCLogFiles > 1) {
|
||||
+ if (OverWriteOldestGCLog) {
|
||||
+ _cur_file_num = next_file_number(_file_name);
|
||||
+ }
|
||||
char tempbuf[JVM_MAXPATHLEN];
|
||||
jio_snprintf(tempbuf, sizeof(tempbuf), "%s.%d" CURRENTAPPX, _file_name, _cur_file_num);
|
||||
_file = fopen(tempbuf, "w");
|
||||
--
|
||||
2.22.0
|
||||
|
||||
311
add-0010-8301749-Tracking-malloc-pooled-memory-size.patch
Normal file
311
add-0010-8301749-Tracking-malloc-pooled-memory-size.patch
Normal file
@ -0,0 +1,311 @@
|
||||
From fe0409dd4a7b26a623d2e0ad77be635b20f11d29 Mon Sep 17 00:00:00 2001
|
||||
Date: Thu, 21 Sep 2023 14:44:51 +0800
|
||||
Subject: add 0010-8301749-Tracking-malloc-pooled-memory-size
|
||||
|
||||
---
|
||||
hotspot/src/os/linux/vm/mallocInfoDcmd.cpp | 62 +++++++++++++++++++
|
||||
hotspot/src/os/linux/vm/mallocInfoDcmd.hpp | 51 +++++++++++++++
|
||||
hotspot/src/os/linux/vm/os_linux.cpp | 10 +++
|
||||
hotspot/src/os/linux/vm/os_linux.hpp | 4 ++
|
||||
.../share/vm/services/diagnosticCommand.cpp | 2 +
|
||||
.../serviceability/dcmd/MallocInfoTest.java | 54 ++++++++++++++++
|
||||
.../com/oracle/java/testlibrary/Platform.java | 18 +++++-
|
||||
7 files changed, 199 insertions(+), 2 deletions(-)
|
||||
create mode 100644 hotspot/src/os/linux/vm/mallocInfoDcmd.cpp
|
||||
create mode 100644 hotspot/src/os/linux/vm/mallocInfoDcmd.hpp
|
||||
create mode 100644 hotspot/test/serviceability/dcmd/MallocInfoTest.java
|
||||
|
||||
diff --git a/hotspot/src/os/linux/vm/mallocInfoDcmd.cpp b/hotspot/src/os/linux/vm/mallocInfoDcmd.cpp
|
||||
new file mode 100644
|
||||
index 000000000..4e50a8e13
|
||||
--- /dev/null
|
||||
+++ b/hotspot/src/os/linux/vm/mallocInfoDcmd.cpp
|
||||
@@ -0,0 +1,62 @@
|
||||
+/*
|
||||
+ * Copyright (c) 2023, Oracle and/or its affiliates. All rights reserved.
|
||||
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
+ *
|
||||
+ * This code is free software; you can redistribute it and/or modify it
|
||||
+ * under the terms of the GNU General Public License version 2 only, as
|
||||
+ * published by the Free Software Foundation.
|
||||
+ *
|
||||
+ * This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
+ * version 2 for more details (a copy is included in the LICENSE file that
|
||||
+ * accompanied this code).
|
||||
+ *
|
||||
+ * You should have received a copy of the GNU General Public License version
|
||||
+ * 2 along with this work; if not, write to the Free Software Foundation,
|
||||
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
+ *
|
||||
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
+ * or visit www.oracle.com if you need additional information or have any
|
||||
+ * questions.
|
||||
+ *
|
||||
+ */
|
||||
+
|
||||
+#include "precompiled.hpp"
|
||||
+#include "mallocInfoDcmd.hpp"
|
||||
+#include "os_linux.hpp"
|
||||
+#include "utilities/globalDefinitions.hpp"
|
||||
+#include "utilities/ostream.hpp"
|
||||
+
|
||||
+#include <malloc.h>
|
||||
+
|
||||
+const char* malloc_info_unavailable = "Error: malloc_info(3) not available.";
|
||||
+
|
||||
+void MallocInfoDcmd::execute(DCmdSource source, TRAPS) {
|
||||
+#ifdef __GLIBC__
|
||||
+ char* buf;
|
||||
+ size_t size;
|
||||
+ FILE* stream = ::open_memstream(&buf, &size);
|
||||
+ if (stream == NULL) {
|
||||
+ _output->print_cr("Error: Could not call malloc_info(3)");
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
+ int err = os::Linux::malloc_info(stream);
|
||||
+ if (err == 0) {
|
||||
+ fflush(stream);
|
||||
+ _output->print_raw(buf);
|
||||
+ _output->cr();
|
||||
+ } else if (err == -1) {
|
||||
+ _output->print_cr("Error: %s", strerror(errno));
|
||||
+ } else if (err == -2) {
|
||||
+ _output->print_cr("%s", malloc_info_unavailable);
|
||||
+ } else {
|
||||
+ ShouldNotReachHere();
|
||||
+ }
|
||||
+ ::fclose(stream);
|
||||
+ ::free(buf);
|
||||
+#else
|
||||
+ _output->print_cr(malloc_info_unavailable);
|
||||
+#endif // __GLIBC__
|
||||
+}
|
||||
diff --git a/hotspot/src/os/linux/vm/mallocInfoDcmd.hpp b/hotspot/src/os/linux/vm/mallocInfoDcmd.hpp
|
||||
new file mode 100644
|
||||
index 000000000..deb154415
|
||||
--- /dev/null
|
||||
+++ b/hotspot/src/os/linux/vm/mallocInfoDcmd.hpp
|
||||
@@ -0,0 +1,51 @@
|
||||
+/*
|
||||
+ * Copyright (c) 2023, Oracle and/or its affiliates. All rights reserved.
|
||||
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
+ *
|
||||
+ * This code is free software; you can redistribute it and/or modify it
|
||||
+ * under the terms of the GNU General Public License version 2 only, as
|
||||
+ * published by the Free Software Foundation.
|
||||
+ *
|
||||
+ * This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
+ * version 2 for more details (a copy is included in the LICENSE file that
|
||||
+ * accompanied this code).
|
||||
+ *
|
||||
+ * You should have received a copy of the GNU General Public License version
|
||||
+ * 2 along with this work; if not, write to the Free Software Foundation,
|
||||
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
+ *
|
||||
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
+ * or visit www.oracle.com if you need additional information or have any
|
||||
+ * questions.
|
||||
+ *
|
||||
+ */
|
||||
+
|
||||
+#ifndef OS_LINUX_MALLOCINFODCMD_HPP
|
||||
+#define OS_LINUX_MALLOCINFODCMD_HPP
|
||||
+
|
||||
+#include "services/diagnosticCommand.hpp"
|
||||
+
|
||||
+class outputStream;
|
||||
+
|
||||
+class MallocInfoDcmd : public DCmd {
|
||||
+public:
|
||||
+ MallocInfoDcmd(outputStream* output, bool heap) : DCmd(output, heap) {}
|
||||
+ static const char* name() {
|
||||
+ return "System.native_heap_info";
|
||||
+ }
|
||||
+ static const char* description() {
|
||||
+ return "Attempts to output information regarding native heap usage through malloc_info(3). If unsuccessful outputs \"Error: \" and a reason.";
|
||||
+ }
|
||||
+ static const char* impact() {
|
||||
+ return "Low";
|
||||
+ }
|
||||
+ static const JavaPermission permission() {
|
||||
+ JavaPermission p = { "java.lang.management.ManagementPermission", "monitor", NULL };
|
||||
+ return p;
|
||||
+ }
|
||||
+ void execute(DCmdSource source, TRAPS);
|
||||
+};
|
||||
+
|
||||
+#endif // OS_LINUX_MALLOCINFODCMD_HPP
|
||||
diff --git a/hotspot/src/os/linux/vm/os_linux.cpp b/hotspot/src/os/linux/vm/os_linux.cpp
|
||||
index cf3a166aa..72839eb5a 100644
|
||||
--- a/hotspot/src/os/linux/vm/os_linux.cpp
|
||||
+++ b/hotspot/src/os/linux/vm/os_linux.cpp
|
||||
@@ -177,6 +177,8 @@ typedef struct glibc_mallinfo (*mallinfo_func_t)(void);
|
||||
typedef struct os::Linux::glibc_mallinfo2 (*mallinfo2_func_t)(void);
|
||||
static mallinfo_func_t g_mallinfo = NULL;
|
||||
static mallinfo2_func_t g_mallinfo2 = NULL;
|
||||
+typedef int (*malloc_info_func_t)(int options, FILE *stream);
|
||||
+static malloc_info_func_t g_malloc_info = NULL;
|
||||
#endif // __GLIBC__
|
||||
|
||||
static jlong initial_time_count=0;
|
||||
@@ -5416,6 +5418,7 @@ void os::init(void) {
|
||||
#ifdef __GLIBC__
|
||||
g_mallinfo = CAST_TO_FN_PTR(mallinfo_func_t, dlsym(RTLD_DEFAULT, "mallinfo"));
|
||||
g_mallinfo2 = CAST_TO_FN_PTR(mallinfo2_func_t, dlsym(RTLD_DEFAULT, "mallinfo2"));
|
||||
+ g_malloc_info = CAST_TO_FN_PTR(malloc_info_func_t, dlsym(RTLD_DEFAULT, "malloc_info"));
|
||||
#endif // __GLIBC__
|
||||
|
||||
// _main_thread points to the thread that created/loaded the JVM.
|
||||
@@ -7072,6 +7075,13 @@ os::Linux::mallinfo_retval_t os::Linux::get_mallinfo(glibc_mallinfo2* out) {
|
||||
}
|
||||
return os::Linux::ok;
|
||||
}
|
||||
+
|
||||
+int os::Linux::malloc_info(FILE* stream) {
|
||||
+ if (g_malloc_info == NULL) {
|
||||
+ return -2;
|
||||
+ }
|
||||
+ return g_malloc_info(0, stream);
|
||||
+}
|
||||
#endif // __GLIBC__
|
||||
|
||||
// Trim-native support
|
||||
diff --git a/hotspot/src/os/linux/vm/os_linux.hpp b/hotspot/src/os/linux/vm/os_linux.hpp
|
||||
index 39a2b4989..a516335d2 100644
|
||||
--- a/hotspot/src/os/linux/vm/os_linux.hpp
|
||||
+++ b/hotspot/src/os/linux/vm/os_linux.hpp
|
||||
@@ -488,6 +488,10 @@ public:
|
||||
// If we only have mallinfo(), values may be 32-bit truncated, which is signaled via
|
||||
// "ok_but_possibly_wrapped".
|
||||
static mallinfo_retval_t get_mallinfo(glibc_mallinfo2* out);
|
||||
+
|
||||
+ // Calls out to GNU extension malloc_info if available
|
||||
+ // otherwise does nothing and returns -2.
|
||||
+ static int malloc_info(FILE* stream);
|
||||
#endif
|
||||
|
||||
static bool isbound_to_all_node() {
|
||||
diff --git a/hotspot/src/share/vm/services/diagnosticCommand.cpp b/hotspot/src/share/vm/services/diagnosticCommand.cpp
|
||||
index 50050a169..416dc77ce 100644
|
||||
--- a/hotspot/src/share/vm/services/diagnosticCommand.cpp
|
||||
+++ b/hotspot/src/share/vm/services/diagnosticCommand.cpp
|
||||
@@ -39,6 +39,7 @@
|
||||
|
||||
#ifdef LINUX
|
||||
#include "trimCHeapDCmd.hpp"
|
||||
+#include "mallocInfoDcmd.hpp"
|
||||
#endif
|
||||
|
||||
PRAGMA_FORMAT_MUTE_WARNINGS_FOR_GCC
|
||||
@@ -79,6 +80,7 @@ void DCmdRegistrant::register_dcmds(){
|
||||
DCmdFactory::register_DCmdFactory(new DCmdFactoryImpl<TouchedMethodsDCmd>(full_export, true, false));
|
||||
#ifdef LINUX
|
||||
DCmdFactory::register_DCmdFactory(new DCmdFactoryImpl<TrimCLibcHeapDCmd>(full_export, true, false));
|
||||
+ DCmdFactory::register_DCmdFactory(new DCmdFactoryImpl<MallocInfoDcmd>(full_export, true, false));
|
||||
#endif // LINUX
|
||||
|
||||
// Enhanced JMX Agent Support
|
||||
diff --git a/hotspot/test/serviceability/dcmd/MallocInfoTest.java b/hotspot/test/serviceability/dcmd/MallocInfoTest.java
|
||||
new file mode 100644
|
||||
index 000000000..bc8ab3ef4
|
||||
--- /dev/null
|
||||
+++ b/hotspot/test/serviceability/dcmd/MallocInfoTest.java
|
||||
@@ -0,0 +1,54 @@
|
||||
+/*
|
||||
+ * Copyright (c) 2023, Oracle and/or its affiliates. All rights reserved.
|
||||
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
+ *
|
||||
+ * This code is free software; you can redistribute it and/or modify it
|
||||
+ * under the terms of the GNU General Public License version 2 only, as
|
||||
+ * published by the Free Software Foundation.
|
||||
+ *
|
||||
+ * This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
+ * version 2 for more details (a copy is included in the LICENSE file that
|
||||
+ * accompanied this code).
|
||||
+ *
|
||||
+ * You should have received a copy of the GNU General Public License version
|
||||
+ * 2 along with this work; if not, write to the Free Software Foundation,
|
||||
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
+ *
|
||||
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
+ * or visit www.oracle.com if you need additional information or have any
|
||||
+ * questions.
|
||||
+ */
|
||||
+
|
||||
+import org.testng.annotations.Test;
|
||||
+import com.oracle.java.testlibrary.*;
|
||||
+
|
||||
+/*
|
||||
+ * @test
|
||||
+ * @summary Test of diagnostic command System.native_heap_info
|
||||
+ * @library /testlibrary
|
||||
+ * @requires (os.family=="linux")
|
||||
+ * @modules java.base/jdk.internal.misc
|
||||
+ * java.compiler
|
||||
+ * java.management
|
||||
+ * jdk.internal.jvmstat/sun.jvmstat.monitor
|
||||
+ * @run testng MallocInfoTest
|
||||
+ */
|
||||
+public class MallocInfoTest {
|
||||
+ public void run(CommandExecutor executor) {
|
||||
+ OutputAnalyzer output = executor.execute("System.native_heap_info");
|
||||
+ if (!Platform.isMusl()) {
|
||||
+ output.shouldNotContain("Error: ");
|
||||
+ output.shouldContain("<malloc version=");
|
||||
+ } else {
|
||||
+ output.shouldContain("Error: malloc_info(3) not available.");
|
||||
+ }
|
||||
+ output.reportDiagnosticSummary();
|
||||
+ }
|
||||
+
|
||||
+ @Test
|
||||
+ public void jmx() {
|
||||
+ run(new JMXExecutor());
|
||||
+ }
|
||||
+}
|
||||
diff --git a/hotspot/test/testlibrary/com/oracle/java/testlibrary/Platform.java b/hotspot/test/testlibrary/com/oracle/java/testlibrary/Platform.java
|
||||
index 6a1407934..adce2ee35 100644
|
||||
--- a/hotspot/test/testlibrary/com/oracle/java/testlibrary/Platform.java
|
||||
+++ b/hotspot/test/testlibrary/com/oracle/java/testlibrary/Platform.java
|
||||
@@ -26,7 +26,8 @@ package com.oracle.java.testlibrary;
|
||||
import java.util.regex.Pattern;
|
||||
|
||||
import com.oracle.java.testlibrary.Utils;
|
||||
-
|
||||
+import java.io.BufferedReader;
|
||||
+import java.io.InputStreamReader;
|
||||
public class Platform {
|
||||
private static final String osName = System.getProperty("os.name");
|
||||
private static final String dataModel = System.getProperty("sun.arch.data.model");
|
||||
@@ -98,7 +99,20 @@ public class Platform {
|
||||
public static String getVMVersion() {
|
||||
return vmVersion;
|
||||
}
|
||||
-
|
||||
+
|
||||
+ public static boolean isMusl() {
|
||||
+ try {
|
||||
+ ProcessBuilder pb = new ProcessBuilder("ldd", "--version");
|
||||
+ pb.redirectErrorStream(true);
|
||||
+ Process p = pb.start();
|
||||
+ BufferedReader b = new BufferedReader(new InputStreamReader(p.getInputStream()));
|
||||
+ String l = b.readLine();
|
||||
+ if (l != null && l.contains("musl")) { return true; }
|
||||
+ } catch(Exception e) {
|
||||
+ }
|
||||
+ return false;
|
||||
+ }
|
||||
+
|
||||
// Returns true for sparc and sparcv9.
|
||||
public static boolean isSparc() {
|
||||
return isArch("sparc.*");
|
||||
--
|
||||
2.22.0
|
||||
|
||||
645
add-6899049-G1-Clean-up-code-in-ptrQueue.-ch-pp-and-.patch
Normal file
645
add-6899049-G1-Clean-up-code-in-ptrQueue.-ch-pp-and-.patch
Normal file
@ -0,0 +1,645 @@
|
||||
From 1d8f83e9ab4a39f6f76617bbd627eec062ab00c2 Mon Sep 17 00:00:00 2001
|
||||
Date: Thu, 21 Sep 2023 15:14:53 +0800
|
||||
Subject: add 6899049-G1-Clean-up-code-in-ptrQueue.-ch-pp-and-ptrQ
|
||||
|
||||
---
|
||||
.../gc_implementation/g1/dirtyCardQueue.cpp | 65 +++++++++++++------
|
||||
.../gc_implementation/g1/dirtyCardQueue.hpp | 16 ++---
|
||||
.../vm/gc_implementation/g1/ptrQueue.cpp | 41 +++++++++---
|
||||
.../vm/gc_implementation/g1/ptrQueue.hpp | 58 ++++++++---------
|
||||
.../vm/gc_implementation/g1/satbQueue.cpp | 65 +++++++++----------
|
||||
.../vm/gc_implementation/g1/satbQueue.hpp | 8 +--
|
||||
hotspot/test/gc/g1/TestPtrQueueSize.java | 58 +++++++++++++++++
|
||||
7 files changed, 201 insertions(+), 110 deletions(-)
|
||||
create mode 100644 hotspot/test/gc/g1/TestPtrQueueSize.java
|
||||
|
||||
diff --git a/hotspot/src/share/vm/gc_implementation/g1/dirtyCardQueue.cpp b/hotspot/src/share/vm/gc_implementation/g1/dirtyCardQueue.cpp
|
||||
index 62555c974..52b0ef0ce 100644
|
||||
--- a/hotspot/src/share/vm/gc_implementation/g1/dirtyCardQueue.cpp
|
||||
+++ b/hotspot/src/share/vm/gc_implementation/g1/dirtyCardQueue.cpp
|
||||
@@ -32,6 +32,18 @@
|
||||
#include "runtime/thread.inline.hpp"
|
||||
#include "utilities/workgroup.hpp"
|
||||
|
||||
+DirtyCardQueue::DirtyCardQueue(DirtyCardQueueSet* qset, bool permanent) :
|
||||
+ // Dirty card queues are always active, so we create them with their
|
||||
+ // active field set to true.
|
||||
+ PtrQueue(qset, permanent, true /* active */)
|
||||
+{ }
|
||||
+
|
||||
+DirtyCardQueue::~DirtyCardQueue() {
|
||||
+ if (!is_permanent()) {
|
||||
+ flush();
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
bool DirtyCardQueue::apply_closure(CardTableEntryClosure* cl,
|
||||
bool consume,
|
||||
uint worker_i) {
|
||||
@@ -40,7 +52,9 @@ bool DirtyCardQueue::apply_closure(CardTableEntryClosure* cl,
|
||||
res = apply_closure_to_buffer(cl, _buf, _index, _sz,
|
||||
consume,
|
||||
worker_i);
|
||||
- if (res && consume) _index = _sz;
|
||||
+ if (res && consume) {
|
||||
+ _index = _sz;
|
||||
+ }
|
||||
}
|
||||
return res;
|
||||
}
|
||||
@@ -51,14 +65,18 @@ bool DirtyCardQueue::apply_closure_to_buffer(CardTableEntryClosure* cl,
|
||||
bool consume,
|
||||
uint worker_i) {
|
||||
if (cl == NULL) return true;
|
||||
- for (size_t i = index; i < sz; i += oopSize) {
|
||||
- int ind = byte_index_to_index((int)i);
|
||||
- jbyte* card_ptr = (jbyte*)buf[ind];
|
||||
+ size_t limit = byte_index_to_index(sz);
|
||||
+ for (size_t i = byte_index_to_index(index); i < limit; ++i) {
|
||||
+ jbyte* card_ptr = static_cast<jbyte*>(buf[i]);
|
||||
if (card_ptr != NULL) {
|
||||
// Set the entry to null, so we don't do it again (via the test
|
||||
// above) if we reconsider this buffer.
|
||||
- if (consume) buf[ind] = NULL;
|
||||
- if (!cl->do_card_ptr(card_ptr, worker_i)) return false;
|
||||
+ if (consume) {
|
||||
+ buf[i] = NULL;
|
||||
+ }
|
||||
+ if (!cl->do_card_ptr(card_ptr, worker_i)) {
|
||||
+ return false;
|
||||
+ }
|
||||
}
|
||||
}
|
||||
return true;
|
||||
@@ -71,7 +89,7 @@ bool DirtyCardQueue::apply_closure_to_buffer(CardTableEntryClosure* cl,
|
||||
DirtyCardQueueSet::DirtyCardQueueSet(bool notify_when_complete) :
|
||||
PtrQueueSet(notify_when_complete),
|
||||
_mut_process_closure(NULL),
|
||||
- _shared_dirty_card_queue(this, true /*perm*/),
|
||||
+ _shared_dirty_card_queue(this, true /* permanent */),
|
||||
_free_ids(NULL),
|
||||
_processed_buffers_mut(0), _processed_buffers_rs_thread(0)
|
||||
{
|
||||
@@ -83,13 +101,19 @@ uint DirtyCardQueueSet::num_par_ids() {
|
||||
return (uint)os::initial_active_processor_count();
|
||||
}
|
||||
|
||||
-void DirtyCardQueueSet::initialize(CardTableEntryClosure* cl, Monitor* cbl_mon, Mutex* fl_lock,
|
||||
+void DirtyCardQueueSet::initialize(CardTableEntryClosure* cl,
|
||||
+ Monitor* cbl_mon,
|
||||
+ Mutex* fl_lock,
|
||||
int process_completed_threshold,
|
||||
int max_completed_queue,
|
||||
- Mutex* lock, PtrQueueSet* fl_owner) {
|
||||
+ Mutex* lock,
|
||||
+ DirtyCardQueueSet* fl_owner) {
|
||||
_mut_process_closure = cl;
|
||||
- PtrQueueSet::initialize(cbl_mon, fl_lock, process_completed_threshold,
|
||||
- max_completed_queue, fl_owner);
|
||||
+ PtrQueueSet::initialize(cbl_mon,
|
||||
+ fl_lock,
|
||||
+ process_completed_threshold,
|
||||
+ max_completed_queue,
|
||||
+ fl_owner);
|
||||
set_buffer_size(G1UpdateBufferSize);
|
||||
_shared_dirty_card_queue.set_lock(lock);
|
||||
_free_ids = new FreeIdSet((int) num_par_ids(), _cbl_mon);
|
||||
@@ -103,7 +127,7 @@ void DirtyCardQueueSet::iterate_closure_all_threads(CardTableEntryClosure* cl,
|
||||
bool consume,
|
||||
uint worker_i) {
|
||||
assert(SafepointSynchronize::is_at_safepoint(), "Must be at safepoint.");
|
||||
- for(JavaThread* t = Threads::first(); t; t = t->next()) {
|
||||
+ for (JavaThread* t = Threads::first(); t; t = t->next()) {
|
||||
bool b = t->dirty_card_queue().apply_closure(cl, consume);
|
||||
guarantee(b, "Should not be interrupted.");
|
||||
}
|
||||
@@ -160,8 +184,7 @@ bool DirtyCardQueueSet::mut_process_buffer(void** buf) {
|
||||
}
|
||||
|
||||
|
||||
-BufferNode*
|
||||
-DirtyCardQueueSet::get_completed_buffer(int stop_at) {
|
||||
+BufferNode* DirtyCardQueueSet::get_completed_buffer(int stop_at) {
|
||||
BufferNode* nd = NULL;
|
||||
MutexLockerEx x(_cbl_mon, Mutex::_no_safepoint_check_flag);
|
||||
|
||||
@@ -178,12 +201,11 @@ DirtyCardQueueSet::get_completed_buffer(int stop_at) {
|
||||
_n_completed_buffers--;
|
||||
assert(_n_completed_buffers >= 0, "Invariant");
|
||||
}
|
||||
- debug_only(assert_completed_buffer_list_len_correct_locked());
|
||||
+ DEBUG_ONLY(assert_completed_buffer_list_len_correct_locked());
|
||||
return nd;
|
||||
}
|
||||
|
||||
-bool DirtyCardQueueSet::
|
||||
-apply_closure_to_completed_buffer_helper(CardTableEntryClosure* cl,
|
||||
+bool DirtyCardQueueSet::apply_closure_to_completed_buffer_helper(CardTableEntryClosure* cl,
|
||||
uint worker_i,
|
||||
BufferNode* nd) {
|
||||
if (nd != NULL) {
|
||||
@@ -259,7 +281,7 @@ void DirtyCardQueueSet::clear() {
|
||||
}
|
||||
_n_completed_buffers = 0;
|
||||
_completed_buffers_tail = NULL;
|
||||
- debug_only(assert_completed_buffer_list_len_correct_locked());
|
||||
+ DEBUG_ONLY(assert_completed_buffer_list_len_correct_locked());
|
||||
}
|
||||
while (buffers_to_delete != NULL) {
|
||||
BufferNode* nd = buffers_to_delete;
|
||||
@@ -291,10 +313,11 @@ void DirtyCardQueueSet::concatenate_logs() {
|
||||
for (JavaThread* t = Threads::first(); t; t = t->next()) {
|
||||
DirtyCardQueue& dcq = t->dirty_card_queue();
|
||||
if (dcq.size() != 0) {
|
||||
- void **buf = t->dirty_card_queue().get_buf();
|
||||
+ void **buf = dcq.get_buf();
|
||||
// We must NULL out the unused entries, then enqueue.
|
||||
- for (size_t i = 0; i < t->dirty_card_queue().get_index(); i += oopSize) {
|
||||
- buf[PtrQueue::byte_index_to_index((int)i)] = NULL;
|
||||
+ size_t limit = dcq.byte_index_to_index(dcq.get_index());
|
||||
+ for (size_t i = 0; i < limit; ++i) {
|
||||
+ buf[i] = NULL;
|
||||
}
|
||||
enqueue_complete_buffer(dcq.get_buf(), dcq.get_index());
|
||||
dcq.reinitialize();
|
||||
diff --git a/hotspot/src/share/vm/gc_implementation/g1/dirtyCardQueue.hpp b/hotspot/src/share/vm/gc_implementation/g1/dirtyCardQueue.hpp
|
||||
index 986c0ea3c..250145937 100644
|
||||
--- a/hotspot/src/share/vm/gc_implementation/g1/dirtyCardQueue.hpp
|
||||
+++ b/hotspot/src/share/vm/gc_implementation/g1/dirtyCardQueue.hpp
|
||||
@@ -29,6 +29,7 @@
|
||||
#include "memory/allocation.hpp"
|
||||
|
||||
class FreeIdSet;
|
||||
+class DirtyCardQueueSet;
|
||||
|
||||
// A closure class for processing card table entries. Note that we don't
|
||||
// require these closure objects to be stack-allocated.
|
||||
@@ -42,14 +43,11 @@ public:
|
||||
// A ptrQueue whose elements are "oops", pointers to object heads.
|
||||
class DirtyCardQueue: public PtrQueue {
|
||||
public:
|
||||
- DirtyCardQueue(PtrQueueSet* qset_, bool perm = false) :
|
||||
- // Dirty card queues are always active, so we create them with their
|
||||
- // active field set to true.
|
||||
- PtrQueue(qset_, perm, true /* active */) { }
|
||||
+ DirtyCardQueue(DirtyCardQueueSet* qset, bool permanent = false);
|
||||
|
||||
// Flush before destroying; queue may be used to capture pending work while
|
||||
// doing something else, with auto-flush on completion.
|
||||
- ~DirtyCardQueue() { if (!is_permanent()) flush(); }
|
||||
+ ~DirtyCardQueue();
|
||||
|
||||
// Process queue entries and release resources.
|
||||
void flush() { flush_impl(); }
|
||||
@@ -72,7 +70,6 @@ public:
|
||||
bool consume = true,
|
||||
uint worker_i = 0);
|
||||
void **get_buf() { return _buf;}
|
||||
- void set_buf(void **buf) {_buf = buf;}
|
||||
size_t get_index() { return _index;}
|
||||
void reinitialize() { _buf = 0; _sz = 0; _index = 0;}
|
||||
};
|
||||
@@ -101,10 +98,13 @@ class DirtyCardQueueSet: public PtrQueueSet {
|
||||
public:
|
||||
DirtyCardQueueSet(bool notify_when_complete = true);
|
||||
|
||||
- void initialize(CardTableEntryClosure* cl, Monitor* cbl_mon, Mutex* fl_lock,
|
||||
+ void initialize(CardTableEntryClosure* cl,
|
||||
+ Monitor* cbl_mon,
|
||||
+ Mutex* fl_lock,
|
||||
int process_completed_threshold,
|
||||
int max_completed_queue,
|
||||
- Mutex* lock, PtrQueueSet* fl_owner = NULL);
|
||||
+ Mutex* lock,
|
||||
+ DirtyCardQueueSet* fl_owner = NULL);
|
||||
|
||||
// The number of parallel ids that can be claimed to allow collector or
|
||||
// mutator threads to do card-processing work.
|
||||
diff --git a/hotspot/src/share/vm/gc_implementation/g1/ptrQueue.cpp b/hotspot/src/share/vm/gc_implementation/g1/ptrQueue.cpp
|
||||
index 2845d5186..c92b081c3 100644
|
||||
--- a/hotspot/src/share/vm/gc_implementation/g1/ptrQueue.cpp
|
||||
+++ b/hotspot/src/share/vm/gc_implementation/g1/ptrQueue.cpp
|
||||
@@ -30,24 +30,25 @@
|
||||
#include "runtime/mutexLocker.hpp"
|
||||
#include "runtime/thread.inline.hpp"
|
||||
|
||||
-PtrQueue::PtrQueue(PtrQueueSet* qset, bool perm, bool active) :
|
||||
+PtrQueue::PtrQueue(PtrQueueSet* qset, bool permanent, bool active) :
|
||||
_qset(qset), _buf(NULL), _index(0), _sz(0), _active(active),
|
||||
- _perm(perm), _lock(NULL)
|
||||
+ _permanent(permanent), _lock(NULL)
|
||||
{}
|
||||
|
||||
PtrQueue::~PtrQueue() {
|
||||
- assert(_perm || (_buf == NULL), "queue must be flushed before delete");
|
||||
+ assert(_permanent || (_buf == NULL), "queue must be flushed before delete");
|
||||
}
|
||||
|
||||
void PtrQueue::flush_impl() {
|
||||
- if (!_perm && _buf != NULL) {
|
||||
+ if (!_permanent && _buf != NULL) {
|
||||
if (_index == _sz) {
|
||||
// No work to do.
|
||||
qset()->deallocate_buffer(_buf);
|
||||
} else {
|
||||
// We must NULL out the unused entries, then enqueue.
|
||||
- for (size_t i = 0; i < _index; i += oopSize) {
|
||||
- _buf[byte_index_to_index((int)i)] = NULL;
|
||||
+ size_t limit = byte_index_to_index(_index);
|
||||
+ for (size_t i = 0; i < limit; ++i) {
|
||||
+ _buf[i] = NULL;
|
||||
}
|
||||
qset()->enqueue_complete_buffer(_buf);
|
||||
}
|
||||
@@ -66,8 +67,8 @@ void PtrQueue::enqueue_known_active(void* ptr) {
|
||||
}
|
||||
|
||||
assert(_index > 0, "postcondition");
|
||||
- _index -= oopSize;
|
||||
- _buf[byte_index_to_index((int)_index)] = ptr;
|
||||
+ _index -= sizeof(void*);
|
||||
+ _buf[byte_index_to_index(_index)] = ptr;
|
||||
assert(0 <= _index && _index <= _sz, "Invariant.");
|
||||
}
|
||||
|
||||
@@ -100,6 +101,26 @@ PtrQueueSet::PtrQueueSet(bool notify_when_complete) :
|
||||
_fl_owner = this;
|
||||
}
|
||||
|
||||
+PtrQueueSet::~PtrQueueSet() {
|
||||
+ // There are presently only a couple (derived) instances ever
|
||||
+ // created, and they are permanent, so no harm currently done by
|
||||
+ // doing nothing here.
|
||||
+}
|
||||
+
|
||||
+void PtrQueueSet::initialize(Monitor* cbl_mon,
|
||||
+ Mutex* fl_lock,
|
||||
+ int process_completed_threshold,
|
||||
+ int max_completed_queue,
|
||||
+ PtrQueueSet *fl_owner) {
|
||||
+ _max_completed_queue = max_completed_queue;
|
||||
+ _process_completed_threshold = process_completed_threshold;
|
||||
+ _completed_queue_padding = 0;
|
||||
+ assert(cbl_mon != NULL && fl_lock != NULL, "Init order issue?");
|
||||
+ _cbl_mon = cbl_mon;
|
||||
+ _fl_lock = fl_lock;
|
||||
+ _fl_owner = (fl_owner != NULL) ? fl_owner : this;
|
||||
+}
|
||||
+
|
||||
void** PtrQueueSet::allocate_buffer() {
|
||||
assert(_sz > 0, "Didn't set a buffer size.");
|
||||
MutexLockerEx x(_fl_owner->_fl_lock, Mutex::_no_safepoint_check_flag);
|
||||
@@ -234,7 +255,7 @@ void PtrQueueSet::enqueue_complete_buffer(void** buf, size_t index) {
|
||||
if (_notify_when_complete)
|
||||
_cbl_mon->notify();
|
||||
}
|
||||
- debug_only(assert_completed_buffer_list_len_correct_locked());
|
||||
+ DEBUG_ONLY(assert_completed_buffer_list_len_correct_locked());
|
||||
}
|
||||
|
||||
int PtrQueueSet::completed_buffers_list_length() {
|
||||
@@ -259,7 +280,7 @@ void PtrQueueSet::assert_completed_buffer_list_len_correct_locked() {
|
||||
|
||||
void PtrQueueSet::set_buffer_size(size_t sz) {
|
||||
assert(_sz == 0 && sz > 0, "Should be called only once.");
|
||||
- _sz = sz * oopSize;
|
||||
+ _sz = sz * sizeof(void*);
|
||||
}
|
||||
|
||||
// Merge lists of buffers. Notify the processing threads.
|
||||
diff --git a/hotspot/src/share/vm/gc_implementation/g1/ptrQueue.hpp b/hotspot/src/share/vm/gc_implementation/g1/ptrQueue.hpp
|
||||
index 27404f0a9..9c969b2ad 100644
|
||||
--- a/hotspot/src/share/vm/gc_implementation/g1/ptrQueue.hpp
|
||||
+++ b/hotspot/src/share/vm/gc_implementation/g1/ptrQueue.hpp
|
||||
@@ -40,44 +40,49 @@ class PtrQueueSet;
|
||||
class PtrQueue VALUE_OBJ_CLASS_SPEC {
|
||||
friend class VMStructs;
|
||||
|
||||
-protected:
|
||||
+ // Noncopyable - not defined.
|
||||
+ PtrQueue(const PtrQueue&);
|
||||
+ PtrQueue& operator=(const PtrQueue&);
|
||||
+
|
||||
// The ptr queue set to which this queue belongs.
|
||||
- PtrQueueSet* _qset;
|
||||
+ PtrQueueSet* const _qset;
|
||||
|
||||
// Whether updates should be logged.
|
||||
bool _active;
|
||||
|
||||
+ // If true, the queue is permanent, and doesn't need to deallocate
|
||||
+ // its buffer in the destructor (since that obtains a lock which may not
|
||||
+ // be legally locked by then.
|
||||
+ const bool _permanent;
|
||||
+
|
||||
+protected:
|
||||
// The buffer.
|
||||
void** _buf;
|
||||
- // The index at which an object was last enqueued. Starts at "_sz"
|
||||
+ // The (byte) index at which an object was last enqueued. Starts at "_sz"
|
||||
// (indicating an empty buffer) and goes towards zero.
|
||||
size_t _index;
|
||||
|
||||
- // The size of the buffer.
|
||||
+ // The (byte) size of the buffer.
|
||||
size_t _sz;
|
||||
|
||||
- // If true, the queue is permanent, and doesn't need to deallocate
|
||||
- // its buffer in the destructor (since that obtains a lock which may not
|
||||
- // be legally locked by then.
|
||||
- bool _perm;
|
||||
-
|
||||
// If there is a lock associated with this buffer, this is that lock.
|
||||
Mutex* _lock;
|
||||
|
||||
PtrQueueSet* qset() { return _qset; }
|
||||
- bool is_permanent() const { return _perm; }
|
||||
+ bool is_permanent() const { return _permanent; }
|
||||
|
||||
// Process queue entries and release resources, if not permanent.
|
||||
void flush_impl();
|
||||
|
||||
-public:
|
||||
// Initialize this queue to contain a null buffer, and be part of the
|
||||
// given PtrQueueSet.
|
||||
- PtrQueue(PtrQueueSet* qset, bool perm = false, bool active = false);
|
||||
+ PtrQueue(PtrQueueSet* qset, bool permanent = false, bool active = false);
|
||||
|
||||
// Requires queue flushed or permanent.
|
||||
~PtrQueue();
|
||||
|
||||
+public:
|
||||
+
|
||||
// Associate a lock with a ptr queue.
|
||||
void set_lock(Mutex* lock) { _lock = lock; }
|
||||
|
||||
@@ -129,13 +134,9 @@ public:
|
||||
|
||||
bool is_active() { return _active; }
|
||||
|
||||
- static int byte_index_to_index(int ind) {
|
||||
- assert((ind % oopSize) == 0, "Invariant.");
|
||||
- return ind / oopSize;
|
||||
- }
|
||||
-
|
||||
- static int index_to_byte_index(int byte_ind) {
|
||||
- return byte_ind * oopSize;
|
||||
+ static size_t byte_index_to_index(size_t ind) {
|
||||
+ assert((ind % sizeof(void*)) == 0, "Invariant.");
|
||||
+ return ind / sizeof(void*);
|
||||
}
|
||||
|
||||
// To support compiler.
|
||||
@@ -246,26 +247,21 @@ protected:
|
||||
return false;
|
||||
}
|
||||
|
||||
-public:
|
||||
// Create an empty ptr queue set.
|
||||
PtrQueueSet(bool notify_when_complete = false);
|
||||
+ ~PtrQueueSet();
|
||||
|
||||
// Because of init-order concerns, we can't pass these as constructor
|
||||
// arguments.
|
||||
- void initialize(Monitor* cbl_mon, Mutex* fl_lock,
|
||||
+ void initialize(Monitor* cbl_mon,
|
||||
+ Mutex* fl_lock,
|
||||
int process_completed_threshold,
|
||||
int max_completed_queue,
|
||||
- PtrQueueSet *fl_owner = NULL) {
|
||||
- _max_completed_queue = max_completed_queue;
|
||||
- _process_completed_threshold = process_completed_threshold;
|
||||
- _completed_queue_padding = 0;
|
||||
- assert(cbl_mon != NULL && fl_lock != NULL, "Init order issue?");
|
||||
- _cbl_mon = cbl_mon;
|
||||
- _fl_lock = fl_lock;
|
||||
- _fl_owner = (fl_owner != NULL) ? fl_owner : this;
|
||||
- }
|
||||
+ PtrQueueSet *fl_owner = NULL);
|
||||
+
|
||||
+public:
|
||||
|
||||
- // Return an empty oop array of size _sz (required to be non-zero).
|
||||
+ // Return an empty array of size _sz (required to be non-zero).
|
||||
void** allocate_buffer();
|
||||
|
||||
// Return an empty buffer to the free list. The "buf" argument is
|
||||
diff --git a/hotspot/src/share/vm/gc_implementation/g1/satbQueue.cpp b/hotspot/src/share/vm/gc_implementation/g1/satbQueue.cpp
|
||||
index d423c69ac..8c70b6795 100644
|
||||
--- a/hotspot/src/share/vm/gc_implementation/g1/satbQueue.cpp
|
||||
+++ b/hotspot/src/share/vm/gc_implementation/g1/satbQueue.cpp
|
||||
@@ -35,6 +35,15 @@
|
||||
|
||||
PRAGMA_FORMAT_MUTE_WARNINGS_FOR_GCC
|
||||
|
||||
+ObjPtrQueue::ObjPtrQueue(SATBMarkQueueSet* qset, bool permanent) :
|
||||
+ // SATB queues are only active during marking cycles. We create
|
||||
+ // them with their active field set to false. If a thread is
|
||||
+ // created during a cycle and its SATB queue needs to be activated
|
||||
+ // before the thread starts running, we'll need to set its active
|
||||
+ // field to true. This is done in JavaThread::initialize_queues().
|
||||
+ PtrQueue(qset, permanent, false /* active */)
|
||||
+{ }
|
||||
+
|
||||
void ObjPtrQueue::flush() {
|
||||
// Filter now to possibly save work later. If filtering empties the
|
||||
// buffer then flush_impl can deallocate the buffer.
|
||||
@@ -101,7 +110,6 @@ inline bool requires_marking(const void* entry, G1CollectedHeap* heap) {
|
||||
void ObjPtrQueue::filter() {
|
||||
G1CollectedHeap* g1h = G1CollectedHeap::heap();
|
||||
void** buf = _buf;
|
||||
- size_t sz = _sz;
|
||||
|
||||
if (buf == NULL) {
|
||||
// nothing to do
|
||||
@@ -109,43 +117,37 @@ void ObjPtrQueue::filter() {
|
||||
}
|
||||
|
||||
// Used for sanity checking at the end of the loop.
|
||||
- debug_only(size_t entries = 0; size_t retained = 0;)
|
||||
+ DEBUG_ONLY(size_t entries = 0; size_t retained = 0;)
|
||||
|
||||
- size_t i = sz;
|
||||
- size_t new_index = sz;
|
||||
+ assert(_index <= _sz, "invariant");
|
||||
+ void** limit = &buf[byte_index_to_index(_index)];
|
||||
+ void** src = &buf[byte_index_to_index(_sz)];
|
||||
+ void** dst = src;
|
||||
|
||||
- while (i > _index) {
|
||||
- assert(i > 0, "we should have at least one more entry to process");
|
||||
- i -= oopSize;
|
||||
- debug_only(entries += 1;)
|
||||
- void** p = &buf[byte_index_to_index((int) i)];
|
||||
- void* entry = *p;
|
||||
+ while (limit < src) {
|
||||
+ DEBUG_ONLY(entries += 1;)
|
||||
+ --src;
|
||||
+ void* entry = *src;
|
||||
// NULL the entry so that unused parts of the buffer contain NULLs
|
||||
// at the end. If we are going to retain it we will copy it to its
|
||||
// final place. If we have retained all entries we have visited so
|
||||
// far, we'll just end up copying it to the same place.
|
||||
- *p = NULL;
|
||||
+ *src = NULL;
|
||||
|
||||
if (requires_marking(entry, g1h) && !g1h->isMarkedNext((oop)entry)) {
|
||||
- assert(new_index > 0, "we should not have already filled up the buffer");
|
||||
- new_index -= oopSize;
|
||||
- assert(new_index >= i,
|
||||
- "new_index should never be below i, as we alwaysr compact 'up'");
|
||||
- void** new_p = &buf[byte_index_to_index((int) new_index)];
|
||||
- assert(new_p >= p, "the destination location should never be below "
|
||||
- "the source as we always compact 'up'");
|
||||
- assert(*new_p == NULL,
|
||||
- "we should have already cleared the destination location");
|
||||
- *new_p = entry;
|
||||
- debug_only(retained += 1;)
|
||||
+ --dst;
|
||||
+ assert(*dst == NULL, "filtering destination should be clear");
|
||||
+ *dst = entry;
|
||||
+ DEBUG_ONLY(retained += 1;);
|
||||
}
|
||||
}
|
||||
+ size_t new_index = pointer_delta(dst, buf, 1);
|
||||
|
||||
#ifdef ASSERT
|
||||
- size_t entries_calc = (sz - _index) / oopSize;
|
||||
+ size_t entries_calc = (_sz - _index) / sizeof(void*);
|
||||
assert(entries == entries_calc, "the number of entries we counted "
|
||||
"should match the number of entries we calculated");
|
||||
- size_t retained_calc = (sz - new_index) / oopSize;
|
||||
+ size_t retained_calc = (_sz - new_index) / sizeof(void*);
|
||||
assert(retained == retained_calc, "the number of retained entries we counted "
|
||||
"should match the number of retained entries we calculated");
|
||||
#endif // ASSERT
|
||||
@@ -172,11 +174,8 @@ bool ObjPtrQueue::should_enqueue_buffer() {
|
||||
|
||||
filter();
|
||||
|
||||
- size_t sz = _sz;
|
||||
- size_t all_entries = sz / oopSize;
|
||||
- size_t retained_entries = (sz - _index) / oopSize;
|
||||
- size_t perc = retained_entries * 100 / all_entries;
|
||||
- bool should_enqueue = perc > (size_t) G1SATBBufferEnqueueingThresholdPercent;
|
||||
+ size_t percent_used = ((_sz - _index) * 100) / _sz;
|
||||
+ bool should_enqueue = percent_used > G1SATBBufferEnqueueingThresholdPercent;
|
||||
return should_enqueue;
|
||||
}
|
||||
|
||||
@@ -187,8 +186,8 @@ void ObjPtrQueue::apply_closure_and_empty(SATBBufferClosure* cl) {
|
||||
assert(_index % sizeof(void*) == 0, "invariant");
|
||||
assert(_sz % sizeof(void*) == 0, "invariant");
|
||||
assert(_index <= _sz, "invariant");
|
||||
- cl->do_buffer(_buf + byte_index_to_index((int)_index),
|
||||
- byte_index_to_index((int)(_sz - _index)));
|
||||
+ cl->do_buffer(_buf + byte_index_to_index(_index),
|
||||
+ byte_index_to_index(_sz - _index));
|
||||
_index = _sz;
|
||||
}
|
||||
}
|
||||
@@ -214,7 +213,7 @@ void ObjPtrQueue::print(const char* name,
|
||||
|
||||
SATBMarkQueueSet::SATBMarkQueueSet() :
|
||||
PtrQueueSet(),
|
||||
- _shared_satb_queue(this, true /*perm*/) { }
|
||||
+ _shared_satb_queue(this, true /* permanent */) { }
|
||||
|
||||
void SATBMarkQueueSet::initialize(Monitor* cbl_mon, Mutex* fl_lock,
|
||||
int process_completed_threshold,
|
||||
@@ -301,7 +300,7 @@ bool SATBMarkQueueSet::apply_closure_to_completed_buffer(SATBBufferClosure* cl)
|
||||
// Filtering can result in non-full completed buffers; see
|
||||
// should_enqueue_buffer.
|
||||
assert(_sz % sizeof(void*) == 0, "invariant");
|
||||
- size_t limit = ObjPtrQueue::byte_index_to_index((int)_sz);
|
||||
+ size_t limit = ObjPtrQueue::byte_index_to_index(_sz);
|
||||
for (size_t i = 0; i < limit; ++i) {
|
||||
if (buf[i] != NULL) {
|
||||
// Found the end of the block of NULLs; process the remainder.
|
||||
diff --git a/hotspot/src/share/vm/gc_implementation/g1/satbQueue.hpp b/hotspot/src/share/vm/gc_implementation/g1/satbQueue.hpp
|
||||
index 594895919..6651210a3 100644
|
||||
--- a/hotspot/src/share/vm/gc_implementation/g1/satbQueue.hpp
|
||||
+++ b/hotspot/src/share/vm/gc_implementation/g1/satbQueue.hpp
|
||||
@@ -50,13 +50,7 @@ private:
|
||||
void filter();
|
||||
|
||||
public:
|
||||
- ObjPtrQueue(PtrQueueSet* qset, bool perm = false) :
|
||||
- // SATB queues are only active during marking cycles. We create
|
||||
- // them with their active field set to false. If a thread is
|
||||
- // created during a cycle and its SATB queue needs to be activated
|
||||
- // before the thread starts running, we'll need to set its active
|
||||
- // field to true. This is done in JavaThread::initialize_queues().
|
||||
- PtrQueue(qset, perm, false /* active */) { }
|
||||
+ ObjPtrQueue(SATBMarkQueueSet* qset, bool permanent = false);
|
||||
|
||||
// Process queue entries and free resources.
|
||||
void flush();
|
||||
diff --git a/hotspot/test/gc/g1/TestPtrQueueSize.java b/hotspot/test/gc/g1/TestPtrQueueSize.java
|
||||
new file mode 100644
|
||||
index 000000000..f46c95bec
|
||||
--- /dev/null
|
||||
+++ b/hotspot/test/gc/g1/TestPtrQueueSize.java
|
||||
@@ -0,0 +1,58 @@
|
||||
+/*
|
||||
+ * Copyright (c) 2023, 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 TestPtrQueueSize.java
|
||||
+* @key gc
|
||||
+* @bug 6899049
|
||||
+* @summary Test size of PtrQueue; used by dirtyCardQueue and satbQueue
|
||||
+* @library /testlibrary
|
||||
+*/
|
||||
+
|
||||
+import com.oracle.java.testlibrary.ProcessTools;
|
||||
+import com.oracle.java.testlibrary.OutputAnalyzer;
|
||||
+
|
||||
+ public class TestPtrQueueSize {
|
||||
+ public static void main(String[] args) throws Exception {
|
||||
+
|
||||
+ ProcessBuilder pb = ProcessTools.createJavaProcessBuilder("-XX:+UseG1GC",
|
||||
+ "-XX:G1SATBBufferSize=716M",
|
||||
+ "-Xms1024m",
|
||||
+ "-Xmx4096m",
|
||||
+ SystemGCTest.class.getName());
|
||||
+
|
||||
+ OutputAnalyzer output = new OutputAnalyzer(pb.start());
|
||||
+
|
||||
+ System.out.println("Output:\n" + output.getOutput());
|
||||
+
|
||||
+ output.shouldHaveExitValue(0);
|
||||
+ }
|
||||
+
|
||||
+ static class SystemGCTest {
|
||||
+ public static void main(String [] args) {
|
||||
+ for (int i = 0; i < 500; ++i) {
|
||||
+ byte[] bArray = new byte[1024*1024];
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
\ No newline at end of file
|
||||
--
|
||||
2.22.0
|
||||
|
||||
2911
add-8142508-To-bring-j.u.z.ZipFile-s-native-implemen.patch
Normal file
2911
add-8142508-To-bring-j.u.z.ZipFile-s-native-implemen.patch
Normal file
File diff suppressed because it is too large
Load Diff
52
add-8146431-j.u.z.ZipFile.getEntry-throws-AIOOBE.patch
Normal file
52
add-8146431-j.u.z.ZipFile.getEntry-throws-AIOOBE.patch
Normal file
@ -0,0 +1,52 @@
|
||||
From b6a24b666a1c7536e35afaba4057cc8eac6fe48f Mon Sep 17 00:00:00 2001
|
||||
Date: Thu, 21 Sep 2023 15:25:03 +0800
|
||||
Subject: add 8146431-j.u.z.ZipFile.getEntry-throws-AIOOBE
|
||||
|
||||
---
|
||||
jdk/src/share/classes/java/util/zip/ZipFile.java | 2 +-
|
||||
jdk/test/java/util/zip/ZipFile/TestZipFile.java | 9 ++++++++-
|
||||
2 files changed, 9 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/jdk/src/share/classes/java/util/zip/ZipFile.java b/jdk/src/share/classes/java/util/zip/ZipFile.java
|
||||
index 38b642bdc..36135a9c0 100644
|
||||
--- a/jdk/src/share/classes/java/util/zip/ZipFile.java
|
||||
+++ b/jdk/src/share/classes/java/util/zip/ZipFile.java
|
||||
@@ -1313,7 +1313,7 @@ class ZipFile implements ZipConstants, Closeable {
|
||||
idx = getEntryNext(idx);
|
||||
}
|
||||
/* If not addSlash, or slash is already there, we are done */
|
||||
- if (!addSlash || name[name.length - 1] == '/') {
|
||||
+ if (!addSlash || name.length == 0 || name[name.length - 1] == '/') {
|
||||
return -1;
|
||||
}
|
||||
// Add a slash to the hash code
|
||||
diff --git a/jdk/test/java/util/zip/ZipFile/TestZipFile.java b/jdk/test/java/util/zip/ZipFile/TestZipFile.java
|
||||
index 30bae3bb9..773f47558 100644
|
||||
--- a/jdk/test/java/util/zip/ZipFile/TestZipFile.java
|
||||
+++ b/jdk/test/java/util/zip/ZipFile/TestZipFile.java
|
||||
@@ -24,7 +24,7 @@
|
||||
|
||||
/*
|
||||
* @test
|
||||
- * @bug 8142508
|
||||
+ * @bug 8142508 8146431
|
||||
* @summary Tests various ZipFile apis
|
||||
* @run main/manual TestZipFile
|
||||
*/
|
||||
@@ -230,6 +230,13 @@ public class TestZipFile {
|
||||
}
|
||||
|
||||
static void doTest0(Zip zip, ZipFile zf) throws Throwable {
|
||||
+ // (0) check zero-length entry name, no AIOOBE
|
||||
+ try {
|
||||
+ check(zf.getEntry("") == null);;
|
||||
+ } catch (Throwable t) {
|
||||
+ unexpected(t);
|
||||
+ }
|
||||
+
|
||||
List<ZipEntry> list = new ArrayList(zip.entries.keySet());
|
||||
// (1) check entry list, in expected order
|
||||
if (!check(Arrays.equals(
|
||||
--
|
||||
2.22.0
|
||||
|
||||
79
add-8147940-Modify-testcase-this-test-does-not-assum.patch
Normal file
79
add-8147940-Modify-testcase-this-test-does-not-assum.patch
Normal file
@ -0,0 +1,79 @@
|
||||
From 40b88d64b144bd1b94b2a887c132ec88b3a9a39d Mon Sep 17 00:00:00 2001
|
||||
Date: Thu, 21 Sep 2023 15:26:13 +0800
|
||||
Subject: add 8147940-Modify-testcase-this-test-does-not-assume-th
|
||||
|
||||
---
|
||||
...stG1TraceEagerReclaimHumongousObjects.java | 45 +------------------
|
||||
1 file changed, 1 insertion(+), 44 deletions(-)
|
||||
|
||||
diff --git a/hotspot/test/gc/g1/TestG1TraceEagerReclaimHumongousObjects.java b/hotspot/test/gc/g1/TestG1TraceEagerReclaimHumongousObjects.java
|
||||
index e653554c9..aca54daf6 100644
|
||||
--- a/hotspot/test/gc/g1/TestG1TraceEagerReclaimHumongousObjects.java
|
||||
+++ b/hotspot/test/gc/g1/TestG1TraceEagerReclaimHumongousObjects.java
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
- * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
|
||||
+ * Copyright (c) 2014, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@@ -36,36 +36,6 @@ import java.util.LinkedList;
|
||||
|
||||
public class TestG1TraceEagerReclaimHumongousObjects {
|
||||
public static void main(String[] args) throws Exception {
|
||||
- testGCLogs();
|
||||
- testHumongousObjectGCLogs();
|
||||
- }
|
||||
-
|
||||
- private static void testGCLogs() throws Exception {
|
||||
-
|
||||
- ProcessBuilder pb = ProcessTools.createJavaProcessBuilder("-XX:+UseG1GC",
|
||||
- "-Xms128M",
|
||||
- "-Xmx128M",
|
||||
- "-Xmn16M",
|
||||
- "-XX:G1HeapRegionSize=1M",
|
||||
- "-XX:+PrintGC",
|
||||
- "-XX:+UnlockExperimentalVMOptions",
|
||||
- "-XX:G1LogLevel=finest",
|
||||
- "-XX:+G1TraceEagerReclaimHumongousObjects",
|
||||
- GCTest.class.getName());
|
||||
-
|
||||
- OutputAnalyzer output = new OutputAnalyzer(pb.start());
|
||||
-
|
||||
- // As G1EagerReclaimHumongousObjects is set(default), below logs should be displayed.
|
||||
- // And GCTest doesn't have humongous objects, so values should be zero.
|
||||
- output.shouldContain("[Humongous Reclaim");
|
||||
- output.shouldContain("[Humongous Total: 0]");
|
||||
- output.shouldContain("[Humongous Candidate: 0]");
|
||||
- output.shouldContain("[Humongous Reclaimed: 0]");
|
||||
-
|
||||
- output.shouldHaveExitValue(0);
|
||||
- }
|
||||
-
|
||||
- private static void testHumongousObjectGCLogs() throws Exception {
|
||||
ProcessBuilder pb = ProcessTools.createJavaProcessBuilder("-XX:+UseG1GC",
|
||||
"-Xms128M",
|
||||
"-Xmx128M",
|
||||
@@ -92,19 +62,6 @@ public class TestG1TraceEagerReclaimHumongousObjects {
|
||||
output.shouldHaveExitValue(0);
|
||||
}
|
||||
|
||||
- static class GCTest {
|
||||
- private static byte[] garbage;
|
||||
-
|
||||
- public static void main(String [] args) {
|
||||
- System.out.println("Creating garbage");
|
||||
- // create 128MB of garbage. This should result in at least one GC
|
||||
- for (int i = 0; i < 1024; i++) {
|
||||
- garbage = new byte[128 * 1024];
|
||||
- }
|
||||
- System.out.println("Done");
|
||||
- }
|
||||
- }
|
||||
-
|
||||
static class GCWithHumongousObjectTest {
|
||||
|
||||
public static final int M = 1024*1024;
|
||||
--
|
||||
2.22.0
|
||||
|
||||
45
add-8170831-ZipFile-implementation-no-longer-caches-.patch
Normal file
45
add-8170831-ZipFile-implementation-no-longer-caches-.patch
Normal file
@ -0,0 +1,45 @@
|
||||
From 8e3e20eef3f18d023ffc327a9fae30c34de84773 Mon Sep 17 00:00:00 2001
|
||||
Date: Thu, 21 Sep 2023 15:24:45 +0800
|
||||
Subject: add 8170831-ZipFile-implementation-no-longer-caches-the
|
||||
|
||||
---
|
||||
jdk/src/share/classes/java/util/zip/ZipFile.java | 9 ++++++++-
|
||||
1 file changed, 8 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/jdk/src/share/classes/java/util/zip/ZipFile.java b/jdk/src/share/classes/java/util/zip/ZipFile.java
|
||||
index b6a6c2a48..38b642bdc 100644
|
||||
--- a/jdk/src/share/classes/java/util/zip/ZipFile.java
|
||||
+++ b/jdk/src/share/classes/java/util/zip/ZipFile.java
|
||||
@@ -342,7 +342,9 @@ class ZipFile implements ZipConstants, Closeable {
|
||||
ZipFileInputStream in = null;
|
||||
synchronized (this) {
|
||||
ensureOpen();
|
||||
- if (!zc.isUTF8() && (entry.flag & EFS) != 0) {
|
||||
+ if (Objects.equals(lastEntryName, entry.name)) {
|
||||
+ pos = lastEntryPos;
|
||||
+ } else if (!zc.isUTF8() && (entry.flag & EFS) != 0) {
|
||||
pos = zsrc.getEntryPos(zc.getBytesUTF8(entry.name), false);
|
||||
} else {
|
||||
pos = zsrc.getEntryPos(zc.getBytes(entry.name), false);
|
||||
@@ -533,6 +535,9 @@ class ZipFile implements ZipConstants, Closeable {
|
||||
Spliterator.IMMUTABLE | Spliterator.NONNULL), false);
|
||||
}
|
||||
|
||||
+ private String lastEntryName;
|
||||
+ private int lastEntryPos;
|
||||
+
|
||||
/* Checks ensureOpen() before invoke this method */
|
||||
private ZipEntry getZipEntry(String name, int pos) {
|
||||
byte[] cen = zsrc.cen;
|
||||
@@ -566,6 +571,8 @@ class ZipFile implements ZipConstants, Closeable {
|
||||
e.comment = zc.toString(cen, start, clen);
|
||||
}
|
||||
}
|
||||
+ lastEntryName = e.name;
|
||||
+ lastEntryPos = pos;
|
||||
return e;
|
||||
}
|
||||
|
||||
--
|
||||
2.22.0
|
||||
|
||||
100
add-8191924-Adjust-DelegatingClassLoader-s-metadata-.patch
Normal file
100
add-8191924-Adjust-DelegatingClassLoader-s-metadata-.patch
Normal file
@ -0,0 +1,100 @@
|
||||
From 64123e7422fb9441c8999aaa1ddfdf639295fea1 Mon Sep 17 00:00:00 2001
|
||||
Date: Thu, 21 Sep 2023 15:26:33 +0800
|
||||
Subject: add 8191924-Adjust-DelegatingClassLoader-s-metadata-spac
|
||||
|
||||
---
|
||||
hotspot/src/share/vm/memory/metaspace.cpp | 31 ++++++++++++++++++++---
|
||||
1 file changed, 28 insertions(+), 3 deletions(-)
|
||||
|
||||
diff --git a/hotspot/src/share/vm/memory/metaspace.cpp b/hotspot/src/share/vm/memory/metaspace.cpp
|
||||
index 07259e649..d65a81267 100644
|
||||
--- a/hotspot/src/share/vm/memory/metaspace.cpp
|
||||
+++ b/hotspot/src/share/vm/memory/metaspace.cpp
|
||||
@@ -1206,7 +1206,10 @@ class SpaceManager : public CHeapObj<mtClass> {
|
||||
Mutex* const _lock;
|
||||
|
||||
// Type of metadata allocated.
|
||||
- Metaspace::MetadataType _mdtype;
|
||||
+ const Metaspace::MetadataType _mdtype;
|
||||
+
|
||||
+ // Type of metaspace
|
||||
+ const Metaspace::MetaspaceType _space_type;
|
||||
|
||||
// List of chunks in use by this SpaceManager. Allocations
|
||||
// are done from the current chunk. The list is used for deallocating
|
||||
@@ -1218,6 +1221,10 @@ class SpaceManager : public CHeapObj<mtClass> {
|
||||
// If class space manager, small chunks are unlimited
|
||||
static uint const _small_chunk_limit;
|
||||
|
||||
+ // Maximum number of specialize chunks to allocate for anonymous and delegating
|
||||
+ // metadata space to a SpaceManager
|
||||
+ static uint const _anon_and_delegating_metadata_specialize_chunk_limit;
|
||||
+
|
||||
// Sum of all space in allocated chunks
|
||||
size_t _allocated_blocks_words;
|
||||
|
||||
@@ -1270,6 +1277,7 @@ class SpaceManager : public CHeapObj<mtClass> {
|
||||
|
||||
public:
|
||||
SpaceManager(Metaspace::MetadataType mdtype,
|
||||
+ Metaspace::MetaspaceType space_type,
|
||||
Mutex* lock);
|
||||
~SpaceManager();
|
||||
|
||||
@@ -1385,6 +1393,7 @@ class SpaceManager : public CHeapObj<mtClass> {
|
||||
};
|
||||
|
||||
uint const SpaceManager::_small_chunk_limit = 4;
|
||||
+uint const SpaceManager::_anon_and_delegating_metadata_specialize_chunk_limit = 4;
|
||||
|
||||
const char* SpaceManager::_expand_lock_name =
|
||||
"SpaceManager chunk allocation lock";
|
||||
@@ -3409,6 +3418,20 @@ size_t SpaceManager::calc_chunk_size(size_t word_size) {
|
||||
// once a medium chunk has been allocated, no more small
|
||||
// chunks will be allocated.
|
||||
size_t chunk_word_size;
|
||||
+
|
||||
+ // Special case for anonymous metadata space.
|
||||
+ // Anonymous metadata space is usually small, with majority within 1K - 2K range and
|
||||
+ // rarely about 4K (64-bits JVM).
|
||||
+ // Instead of jumping to SmallChunk after initial chunk exhausted, keeping allocation
|
||||
+ // from SpecializeChunk up to _anon_or_delegating_metadata_specialize_chunk_limit (4)
|
||||
+ // reduces space waste from 60+% to around 30%.
|
||||
+ if ((_space_type == Metaspace::AnonymousMetaspaceType || _space_type == Metaspace::ReflectionMetaspaceType) &&
|
||||
+ _mdtype == Metaspace::NonClassType &&
|
||||
+ sum_count_in_chunks_in_use(SpecializedIndex) < _anon_and_delegating_metadata_specialize_chunk_limit &&
|
||||
+ word_size + Metachunk::overhead() <= SpecializedChunk) {
|
||||
+ return SpecializedChunk;
|
||||
+ }
|
||||
+
|
||||
if (chunks_in_use(MediumIndex) == NULL &&
|
||||
sum_count_in_chunks_in_use(SmallIndex) < _small_chunk_limit) {
|
||||
chunk_word_size = (size_t) small_chunk_size();
|
||||
@@ -3517,8 +3540,10 @@ void SpaceManager::print_on(outputStream* st) const {
|
||||
}
|
||||
|
||||
SpaceManager::SpaceManager(Metaspace::MetadataType mdtype,
|
||||
+ Metaspace::MetaspaceType space_type,
|
||||
Mutex* lock) :
|
||||
_mdtype(mdtype),
|
||||
+ _space_type(space_type),
|
||||
_allocated_blocks_words(0),
|
||||
_allocated_chunks_words(0),
|
||||
_allocated_chunks_count(0),
|
||||
@@ -4926,11 +4951,11 @@ void Metaspace::initialize(Mutex* lock, MetaspaceType type) {
|
||||
verify_global_initialization();
|
||||
|
||||
// Allocate SpaceManager for metadata objects.
|
||||
- _vsm = new SpaceManager(NonClassType, lock);
|
||||
+ _vsm = new SpaceManager(NonClassType, type, lock);
|
||||
|
||||
if (using_class_space()) {
|
||||
// Allocate SpaceManager for classes.
|
||||
- _class_vsm = new SpaceManager(ClassType, lock);
|
||||
+ _class_vsm = new SpaceManager(ClassType, type, lock);
|
||||
} else {
|
||||
_class_vsm = NULL;
|
||||
}
|
||||
--
|
||||
2.22.0
|
||||
|
||||
2770
add-8198423-Improve-metaspace-chunk-allocation.patch
Normal file
2770
add-8198423-Improve-metaspace-chunk-allocation.patch
Normal file
File diff suppressed because it is too large
Load Diff
274
add-8226530-ZipFile-reads-wrong-entry-size-from-ZIP6.patch
Normal file
274
add-8226530-ZipFile-reads-wrong-entry-size-from-ZIP6.patch
Normal file
@ -0,0 +1,274 @@
|
||||
From 131462b71b86d97bd7dadf7a099d4395d9057423 Mon Sep 17 00:00:00 2001
|
||||
Date: Thu, 21 Sep 2023 15:16:36 +0800
|
||||
Subject: add 8226530-ZipFile-reads-wrong-entry-size-from-ZIP64-en
|
||||
|
||||
---
|
||||
.../share/classes/java/util/zip/ZipEntry.java | 41 +++--
|
||||
.../share/classes/java/util/zip/ZipFile.java | 2 +-
|
||||
.../classes/java/util/zip/ZipInputStream.java | 4 +-
|
||||
.../java/util/zip/ZipFile/Zip64SizeTest.java | 147 ++++++++++++++++++
|
||||
4 files changed, 179 insertions(+), 15 deletions(-)
|
||||
create mode 100644 jdk/test/java/util/zip/ZipFile/Zip64SizeTest.java
|
||||
|
||||
diff --git a/jdk/src/share/classes/java/util/zip/ZipEntry.java b/jdk/src/share/classes/java/util/zip/ZipEntry.java
|
||||
index aa93bcb36..4a15428ac 100644
|
||||
--- a/jdk/src/share/classes/java/util/zip/ZipEntry.java
|
||||
+++ b/jdk/src/share/classes/java/util/zip/ZipEntry.java
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
- * Copyright (c) 1995, 2015, Oracle and/or its affiliates. All rights reserved.
|
||||
+ * Copyright (c) 1995, 2019, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@@ -440,7 +440,7 @@ class ZipEntry implements ZipConstants, Cloneable {
|
||||
* @see #getExtra()
|
||||
*/
|
||||
public void setExtra(byte[] extra) {
|
||||
- setExtra0(extra, false);
|
||||
+ setExtra0(extra, false, true);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -450,8 +450,11 @@ class ZipEntry implements ZipConstants, Cloneable {
|
||||
* the extra field data bytes
|
||||
* @param doZIP64
|
||||
* if true, set size and csize from ZIP64 fields if present
|
||||
+ * @param isLOC
|
||||
+ * true if setting the extra field for a LOC, false if for
|
||||
+ * a CEN
|
||||
*/
|
||||
- void setExtra0(byte[] extra, boolean doZIP64) {
|
||||
+ void setExtra0(byte[] extra, boolean doZIP64, boolean isLOC) {
|
||||
if (extra != null) {
|
||||
if (extra.length > 0xFFFF) {
|
||||
throw new IllegalArgumentException("invalid extra field length");
|
||||
@@ -468,15 +471,29 @@ class ZipEntry implements ZipConstants, Cloneable {
|
||||
switch (tag) {
|
||||
case EXTID_ZIP64:
|
||||
if (doZIP64) {
|
||||
- // LOC extra zip64 entry MUST include BOTH original
|
||||
- // and compressed file size fields.
|
||||
- // If invalid zip64 extra fields, simply skip. Even
|
||||
- // it's rare, it's possible the entry size happens to
|
||||
- // be the magic value and it "accidently" has some
|
||||
- // bytes in extra match the id.
|
||||
- if (sz >= 16) {
|
||||
- size = get64(extra, off);
|
||||
- csize = get64(extra, off + 8);
|
||||
+ if (isLOC) {
|
||||
+ // LOC extra zip64 entry MUST include BOTH original
|
||||
+ // and compressed file size fields.
|
||||
+ // If invalid zip64 extra fields, simply skip. Even
|
||||
+ // it's rare, it's possible the entry size happens to
|
||||
+ // be the magic value and it "accidently" has some
|
||||
+ // bytes in extra match the id.
|
||||
+ if (sz >= 16) {
|
||||
+ size = get64(extra, off);
|
||||
+ csize = get64(extra, off + 8);
|
||||
+ }
|
||||
+ } else {
|
||||
+ // CEN extra zip64
|
||||
+ if (size == ZIP64_MAGICVAL) {
|
||||
+ if (off + 8 > len) // invalid zip64 extra
|
||||
+ break; // fields, just skip
|
||||
+ size = get64(extra, off);
|
||||
+ }
|
||||
+ if (csize == ZIP64_MAGICVAL) {
|
||||
+ if (off + 16 > len) // invalid zip64 extra
|
||||
+ break; // fields, just skip
|
||||
+ csize = get64(extra, off + 8);
|
||||
+ }
|
||||
}
|
||||
}
|
||||
break;
|
||||
diff --git a/jdk/src/share/classes/java/util/zip/ZipFile.java b/jdk/src/share/classes/java/util/zip/ZipFile.java
|
||||
index 5d9b0de97..9e854e84d 100644
|
||||
--- a/jdk/src/share/classes/java/util/zip/ZipFile.java
|
||||
+++ b/jdk/src/share/classes/java/util/zip/ZipFile.java
|
||||
@@ -556,7 +556,7 @@ class ZipFile implements ZipConstants, Closeable {
|
||||
e.method = CENHOW(cen, pos);
|
||||
if (elen != 0) {
|
||||
int start = pos + CENHDR + nlen;
|
||||
- e.setExtra0(Arrays.copyOfRange(cen, start, start + elen), true);
|
||||
+ e.setExtra0(Arrays.copyOfRange(cen, start, start + elen), true, false);
|
||||
}
|
||||
if (clen != 0) {
|
||||
int start = pos + CENHDR + nlen + elen;
|
||||
diff --git a/jdk/src/share/classes/java/util/zip/ZipInputStream.java b/jdk/src/share/classes/java/util/zip/ZipInputStream.java
|
||||
index 98526ef82..398dd70ad 100644
|
||||
--- a/jdk/src/share/classes/java/util/zip/ZipInputStream.java
|
||||
+++ b/jdk/src/share/classes/java/util/zip/ZipInputStream.java
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
- * Copyright (c) 1996, 2015, Oracle and/or its affiliates. All rights reserved.
|
||||
+ * Copyright (c) 1996, 2019, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@@ -320,7 +320,7 @@ class ZipInputStream extends InflaterInputStream implements ZipConstants {
|
||||
byte[] extra = new byte[len];
|
||||
readFully(extra, 0, len);
|
||||
e.setExtra0(extra,
|
||||
- e.csize == ZIP64_MAGICVAL || e.size == ZIP64_MAGICVAL);
|
||||
+ e.csize == ZIP64_MAGICVAL || e.size == ZIP64_MAGICVAL, true);
|
||||
}
|
||||
return e;
|
||||
}
|
||||
diff --git a/jdk/test/java/util/zip/ZipFile/Zip64SizeTest.java b/jdk/test/java/util/zip/ZipFile/Zip64SizeTest.java
|
||||
new file mode 100644
|
||||
index 000000000..be701e480
|
||||
--- /dev/null
|
||||
+++ b/jdk/test/java/util/zip/ZipFile/Zip64SizeTest.java
|
||||
@@ -0,0 +1,147 @@
|
||||
+/*
|
||||
+ * Copyright (c) 2019, Oracle and/or its affiliates. All rights reserved.
|
||||
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
+ *
|
||||
+ * This code is free software; you can redistribute it and/or modify it
|
||||
+ * under the terms of the GNU General Public License version 2 only, as
|
||||
+ * published by the Free Software Foundation.
|
||||
+ *
|
||||
+ * This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
+ * version 2 for more details (a copy is included in the LICENSE file that
|
||||
+ * accompanied this code).
|
||||
+ *
|
||||
+ * You should have received a copy of the GNU General Public License version
|
||||
+ * 2 along with this work; if not, write to the Free Software Foundation,
|
||||
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
+ *
|
||||
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
+ * or visit www.oracle.com if you need additional information or have any
|
||||
+ * questions.
|
||||
+ */
|
||||
+import org.testng.annotations.AfterMethod;
|
||||
+import org.testng.annotations.BeforeMethod;
|
||||
+import org.testng.annotations.Test;
|
||||
+
|
||||
+import java.io.*;
|
||||
+import java.nio.file.Files;
|
||||
+import java.nio.file.Path;
|
||||
+import java.util.List;
|
||||
+import java.util.zip.ZipEntry;
|
||||
+import java.util.zip.ZipFile;
|
||||
+import java.util.zip.ZipOutputStream;
|
||||
+
|
||||
+import static org.testng.Assert.assertTrue;
|
||||
+
|
||||
+/**
|
||||
+ * @test
|
||||
+ * @bug 8226530
|
||||
+ * @summary ZIP File System tests that leverage DirectoryStream
|
||||
+ * @modules java.base
|
||||
+ * @compile Zip64SizeTest.java
|
||||
+ * @run testng Zip64SizeTest
|
||||
+ */
|
||||
+public class Zip64SizeTest {
|
||||
+
|
||||
+ private static final int BUFFER_SIZE = 2048;
|
||||
+ // ZIP file to create
|
||||
+ private static final String ZIP_FILE_NAME = "Zip64SizeTest.zip";
|
||||
+ // File that will be created with a size greater than 0xFFFFFFFF
|
||||
+ private static final String LARGE_FILE_NAME = "LargeZipEntry.txt";
|
||||
+ // File that will be created with a size less than 0xFFFFFFFF
|
||||
+ private static final String SMALL_FILE_NAME = "SmallZipEntry.txt";
|
||||
+ // List of files to be added to the ZIP file
|
||||
+ private static final List<String> ZIP_ENTRIES = List.of(LARGE_FILE_NAME,
|
||||
+ SMALL_FILE_NAME);
|
||||
+ private static final long LARGE_FILE_SIZE = 5L * 1024L * 1024L * 1024L; // 5GB
|
||||
+ private static final long SMALL_FILE_SIZE = 0x100000L; // 1024L x 1024L;
|
||||
+
|
||||
+ /**
|
||||
+ * Validate that if the size of a ZIP entry exceeds 0xFFFFFFFF, that the
|
||||
+ * correct size is returned from the ZIP64 Extended information.
|
||||
+ * @throws IOException
|
||||
+ */
|
||||
+ @Test
|
||||
+ private static void validateZipEntrySizes() throws IOException {
|
||||
+ createFiles();
|
||||
+ createZipFile();
|
||||
+ System.out.println("Validating Zip Entry Sizes");
|
||||
+ try (ZipFile zip = new ZipFile(ZIP_FILE_NAME)) {
|
||||
+ ZipEntry ze = zip.getEntry(LARGE_FILE_NAME);
|
||||
+ System.out.printf("Entry: %s, size= %s%n", ze.getName(), ze.getSize());
|
||||
+ assertTrue(ze.getSize() == LARGE_FILE_SIZE);
|
||||
+ ze = zip.getEntry(SMALL_FILE_NAME);
|
||||
+ System.out.printf("Entry: %s, size= %s%n", ze.getName(), ze.getSize());
|
||||
+ assertTrue(ze.getSize() == SMALL_FILE_SIZE);
|
||||
+
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ /**
|
||||
+ * Delete the files created for use by the test
|
||||
+ * @throws IOException if an error occurs deleting the files
|
||||
+ */
|
||||
+ private static void deleteFiles() throws IOException {
|
||||
+ Files.deleteIfExists(Path.of(ZIP_FILE_NAME));
|
||||
+ Files.deleteIfExists(Path.of(LARGE_FILE_NAME));
|
||||
+ Files.deleteIfExists(Path.of(SMALL_FILE_NAME));
|
||||
+ }
|
||||
+
|
||||
+ /**
|
||||
+ * Create the ZIP file adding an entry whose size exceeds 0xFFFFFFFF
|
||||
+ * @throws IOException if an error occurs creating the ZIP File
|
||||
+ */
|
||||
+ private static void createZipFile() throws IOException {
|
||||
+ try (FileOutputStream fos = new FileOutputStream(ZIP_FILE_NAME);
|
||||
+ ZipOutputStream zos = new ZipOutputStream(fos)) {
|
||||
+ System.out.printf("Creating Zip file: %s%n", ZIP_FILE_NAME);
|
||||
+ for (String srcFile : ZIP_ENTRIES) {
|
||||
+ System.out.printf("...Adding Entry: %s%n", srcFile);
|
||||
+ File fileToZip = new File(srcFile);
|
||||
+ try (FileInputStream fis = new FileInputStream(fileToZip)) {
|
||||
+ ZipEntry zipEntry = new ZipEntry(fileToZip.getName());
|
||||
+ zipEntry.setSize(fileToZip.length());
|
||||
+ zos.putNextEntry(zipEntry);
|
||||
+ byte[] bytes = new byte[BUFFER_SIZE];
|
||||
+ int length;
|
||||
+ while ((length = fis.read(bytes)) >= 0) {
|
||||
+ zos.write(bytes, 0, length);
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ /**
|
||||
+ * Create the files that will be added to the ZIP file
|
||||
+ * @throws IOException if there is a problem creating the files
|
||||
+ */
|
||||
+ private static void createFiles() throws IOException {
|
||||
+ try (RandomAccessFile largeFile = new RandomAccessFile(LARGE_FILE_NAME, "rw");
|
||||
+ RandomAccessFile smallFile = new RandomAccessFile(SMALL_FILE_NAME, "rw")) {
|
||||
+ System.out.printf("Creating %s%n", LARGE_FILE_NAME);
|
||||
+ largeFile.setLength(LARGE_FILE_SIZE);
|
||||
+ System.out.printf("Creating %s%n", SMALL_FILE_NAME);
|
||||
+ smallFile.setLength(SMALL_FILE_SIZE);
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ /**
|
||||
+ * Make sure the needed test files do not exist prior to executing the test
|
||||
+ * @throws IOException
|
||||
+ */
|
||||
+ @BeforeMethod
|
||||
+ public void setUp() throws IOException {
|
||||
+ deleteFiles();
|
||||
+ }
|
||||
+
|
||||
+ /**
|
||||
+ * Remove the files created for the test
|
||||
+ * @throws IOException
|
||||
+ */
|
||||
+ @AfterMethod
|
||||
+ public void tearDown() throws IOException {
|
||||
+ deleteFiles();
|
||||
+ }
|
||||
+}
|
||||
\ No newline at end of file
|
||||
--
|
||||
2.22.0
|
||||
|
||||
54
add-8226530-test-case-fixed.patch
Normal file
54
add-8226530-test-case-fixed.patch
Normal file
@ -0,0 +1,54 @@
|
||||
From 6430afa36959aa740f47d64427f06c755ea1549f Mon Sep 17 00:00:00 2001
|
||||
Date: Thu, 21 Sep 2023 15:25:27 +0800
|
||||
Subject: add 8226530-test-case-fixed
|
||||
|
||||
---
|
||||
jdk/test/java/util/zip/ZipFile/Zip64SizeTest.java | 13 +++++++------
|
||||
1 file changed, 7 insertions(+), 6 deletions(-)
|
||||
|
||||
diff --git a/jdk/test/java/util/zip/ZipFile/Zip64SizeTest.java b/jdk/test/java/util/zip/ZipFile/Zip64SizeTest.java
|
||||
index be701e480..c466ffa07 100644
|
||||
--- a/jdk/test/java/util/zip/ZipFile/Zip64SizeTest.java
|
||||
+++ b/jdk/test/java/util/zip/ZipFile/Zip64SizeTest.java
|
||||
@@ -26,7 +26,8 @@ import org.testng.annotations.Test;
|
||||
|
||||
import java.io.*;
|
||||
import java.nio.file.Files;
|
||||
-import java.nio.file.Path;
|
||||
+import java.nio.file.Paths;
|
||||
+import java.util.Arrays;
|
||||
import java.util.List;
|
||||
import java.util.zip.ZipEntry;
|
||||
import java.util.zip.ZipFile;
|
||||
@@ -52,7 +53,7 @@ public class Zip64SizeTest {
|
||||
// File that will be created with a size less than 0xFFFFFFFF
|
||||
private static final String SMALL_FILE_NAME = "SmallZipEntry.txt";
|
||||
// List of files to be added to the ZIP file
|
||||
- private static final List<String> ZIP_ENTRIES = List.of(LARGE_FILE_NAME,
|
||||
+ private static final List<String> ZIP_ENTRIES = Arrays.asList(LARGE_FILE_NAME,
|
||||
SMALL_FILE_NAME);
|
||||
private static final long LARGE_FILE_SIZE = 5L * 1024L * 1024L * 1024L; // 5GB
|
||||
private static final long SMALL_FILE_SIZE = 0x100000L; // 1024L x 1024L;
|
||||
@@ -83,9 +84,9 @@ public class Zip64SizeTest {
|
||||
* @throws IOException if an error occurs deleting the files
|
||||
*/
|
||||
private static void deleteFiles() throws IOException {
|
||||
- Files.deleteIfExists(Path.of(ZIP_FILE_NAME));
|
||||
- Files.deleteIfExists(Path.of(LARGE_FILE_NAME));
|
||||
- Files.deleteIfExists(Path.of(SMALL_FILE_NAME));
|
||||
+ Files.deleteIfExists(Paths.get(ZIP_FILE_NAME));
|
||||
+ Files.deleteIfExists(Paths.get(LARGE_FILE_NAME));
|
||||
+ Files.deleteIfExists(Paths.get(SMALL_FILE_NAME));
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -144,4 +145,4 @@ public class Zip64SizeTest {
|
||||
public void tearDown() throws IOException {
|
||||
deleteFiles();
|
||||
}
|
||||
-}
|
||||
\ No newline at end of file
|
||||
+}
|
||||
--
|
||||
2.22.0
|
||||
|
||||
23
add-8227041-runtime-memory-RunUnitTestsConcurrently.patch
Normal file
23
add-8227041-runtime-memory-RunUnitTestsConcurrently.patch
Normal file
@ -0,0 +1,23 @@
|
||||
From 627e452a58f0c8fc5504ec2ccd3de69924ab1484 Mon Sep 17 00:00:00 2001
|
||||
Date: Fri, 22 Sep 2023 14:45:50 +0800
|
||||
Subject: add 8227041-runtime-memory-RunUnitTestsConcurrently
|
||||
|
||||
---
|
||||
hotspot/src/share/vm/memory/metaspace.cpp | 1 -
|
||||
1 file changed, 1 deletion(-)
|
||||
|
||||
diff --git a/hotspot/src/share/vm/memory/metaspace.cpp b/hotspot/src/share/vm/memory/metaspace.cpp
|
||||
index d65a81267..0569500c1 100644
|
||||
--- a/hotspot/src/share/vm/memory/metaspace.cpp
|
||||
+++ b/hotspot/src/share/vm/memory/metaspace.cpp
|
||||
@@ -5432,7 +5432,6 @@ class TestMetaspaceAuxTest : AllStatic {
|
||||
static void test() {
|
||||
test_reserved();
|
||||
test_committed();
|
||||
- test_virtual_space_list_large_chunk();
|
||||
}
|
||||
};
|
||||
|
||||
--
|
||||
2.22.0
|
||||
|
||||
70
add-8242842-Avoid-reallocating-name-when-checking-fo.patch
Normal file
70
add-8242842-Avoid-reallocating-name-when-checking-fo.patch
Normal file
@ -0,0 +1,70 @@
|
||||
From be90711b32cb79822222d31f258ff4e0f45a616c Mon Sep 17 00:00:00 2001
|
||||
Date: Thu, 21 Sep 2023 15:24:07 +0800
|
||||
Subject: add 8242842-Avoid-reallocating-name-when-checking-for-tr
|
||||
|
||||
---
|
||||
.../share/classes/java/util/zip/ZipFile.java | 25 ++++++++++++-------
|
||||
1 file changed, 16 insertions(+), 9 deletions(-)
|
||||
|
||||
diff --git a/jdk/src/share/classes/java/util/zip/ZipFile.java b/jdk/src/share/classes/java/util/zip/ZipFile.java
|
||||
index 9e854e84d..b6a6c2a48 100644
|
||||
--- a/jdk/src/share/classes/java/util/zip/ZipFile.java
|
||||
+++ b/jdk/src/share/classes/java/util/zip/ZipFile.java
|
||||
@@ -1049,7 +1049,7 @@ class ZipFile implements ZipConstants, Closeable {
|
||||
return h;
|
||||
}
|
||||
|
||||
- private static final int hash_append(int hash, byte b) {
|
||||
+ private static final int hashAppend(int hash, byte b) {
|
||||
return hash * 31 + b;
|
||||
}
|
||||
|
||||
@@ -1267,11 +1267,13 @@ class ZipFile implements ZipConstants, Closeable {
|
||||
}
|
||||
int hsh = hashN(name, 0, name.length);
|
||||
int idx = table[(hsh & 0x7fffffff) % tablelen];
|
||||
+ boolean appendSlash = false;
|
||||
/*
|
||||
* This while loop is an optimization where a double lookup
|
||||
- * for name and name+/ is being performed. The name char
|
||||
- * array has enough room at the end to try again with a
|
||||
- * slash appended if the first table lookup does not succeed.
|
||||
+ * for name and name+/ is being performed. The name byte
|
||||
+ * array will be updated with an added slash only if the first
|
||||
+ * table lookup fails and there is a matching hash value for
|
||||
+ * name+/.
|
||||
*/
|
||||
while(true) {
|
||||
/*
|
||||
@@ -1282,6 +1284,11 @@ class ZipFile implements ZipConstants, Closeable {
|
||||
if (getEntryHash(idx) == hsh) {
|
||||
// The CEN name must match the specfied one
|
||||
int pos = getEntryPos(idx);
|
||||
+ if (appendSlash) {
|
||||
+ name = Arrays.copyOf(name, name.length + 1);
|
||||
+ name[name.length - 1] = '/';
|
||||
+ appendSlash = false;
|
||||
+ }
|
||||
if (name.length == CENNAM(cen, pos)) {
|
||||
boolean matched = true;
|
||||
int nameoff = pos + CENHDR;
|
||||
@@ -1302,11 +1309,11 @@ class ZipFile implements ZipConstants, Closeable {
|
||||
if (!addSlash || name[name.length - 1] == '/') {
|
||||
return -1;
|
||||
}
|
||||
- /* Add slash and try once more */
|
||||
- name = Arrays.copyOf(name, name.length + 1);
|
||||
- name[name.length - 1] = '/';
|
||||
- hsh = hash_append(hsh, (byte)'/');
|
||||
- //idx = table[hsh % tablelen];
|
||||
+ // Add a slash to the hash code
|
||||
+ hsh = hashAppend(hsh, (byte)'/');
|
||||
+ // If we find a match on the new hash code, we need to append a
|
||||
+ // slash when comparing
|
||||
+ appendSlash = true;
|
||||
idx = table[(hsh & 0x7fffffff) % tablelen];
|
||||
addSlash = false;
|
||||
}
|
||||
--
|
||||
2.22.0
|
||||
|
||||
28
add-Adapting-IOException-of-Zip-to-ZipException.patch
Normal file
28
add-Adapting-IOException-of-Zip-to-ZipException.patch
Normal file
@ -0,0 +1,28 @@
|
||||
From 7965b56b3269b8e553ce929a466466990c9d0c07 Mon Sep 17 00:00:00 2001
|
||||
Date: Fri, 22 Sep 2023 14:45:16 +0800
|
||||
Subject: add Adapting-IOException-of-Zip-to-ZipException
|
||||
|
||||
---
|
||||
jdk/src/share/classes/java/util/zip/ZipFile.java | 6 +++++-
|
||||
1 file changed, 5 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/jdk/src/share/classes/java/util/zip/ZipFile.java b/jdk/src/share/classes/java/util/zip/ZipFile.java
|
||||
index 36135a9c0..e603e83d3 100644
|
||||
--- a/jdk/src/share/classes/java/util/zip/ZipFile.java
|
||||
+++ b/jdk/src/share/classes/java/util/zip/ZipFile.java
|
||||
@@ -970,7 +970,11 @@ class ZipFile implements ZipConstants, Closeable {
|
||||
return src;
|
||||
}
|
||||
}
|
||||
- src = new Source(key, toDelete);
|
||||
+ try {
|
||||
+ src = new Source(key, toDelete);
|
||||
+ } catch (IOException exception) {
|
||||
+ throw new ZipException(exception.getMessage());
|
||||
+ }
|
||||
|
||||
synchronized (files) {
|
||||
if (files.containsKey(key)) { // someone else put in first
|
||||
--
|
||||
2.22.0
|
||||
|
||||
26
add-Do-not-collect_class-when-DynamicCDS-dump.patch
Normal file
26
add-Do-not-collect_class-when-DynamicCDS-dump.patch
Normal file
@ -0,0 +1,26 @@
|
||||
From 32657f9ef4e781254fb918adef8802d9998ef083 Mon Sep 17 00:00:00 2001
|
||||
Date: Fri, 22 Sep 2023 14:44:01 +0800
|
||||
Subject: add Do-not-collect_class-when-DynamicCDS-dump
|
||||
|
||||
---
|
||||
hotspot/src/share/vm/classfile/dictionary.cpp | 4 +++-
|
||||
1 file changed, 3 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/hotspot/src/share/vm/classfile/dictionary.cpp b/hotspot/src/share/vm/classfile/dictionary.cpp
|
||||
index 530c3fdfb..79aaa99e5 100644
|
||||
--- a/hotspot/src/share/vm/classfile/dictionary.cpp
|
||||
+++ b/hotspot/src/share/vm/classfile/dictionary.cpp
|
||||
@@ -209,7 +209,9 @@ void Dictionary::remove_classes_in_error_state(void f(Klass*)) {
|
||||
_current_class_entry = NULL;
|
||||
}
|
||||
free_entry(probe);
|
||||
- f(ik);
|
||||
+ if (DumpSharedSpaces) {
|
||||
+ f(ik);
|
||||
+ }
|
||||
ResourceMark rm;
|
||||
tty->print_cr("Preload Warning: Removed error class: %s", ik->external_name());
|
||||
continue;
|
||||
--
|
||||
2.22.0
|
||||
|
||||
153
add-Fix-aarch64-runtime-thread-signal-transfer-bug.patch
Normal file
153
add-Fix-aarch64-runtime-thread-signal-transfer-bug.patch
Normal file
@ -0,0 +1,153 @@
|
||||
From c4fd69c76c41b7b6168f1071d50143566f7d269e Mon Sep 17 00:00:00 2001
|
||||
Date: Fri, 22 Sep 2023 14:48:33 +0800
|
||||
Subject: [PATCH] add Fix-aarch64-runtime-thread-signal-transfer-bug
|
||||
|
||||
---
|
||||
.../src/cpu/aarch64/vm/vm_version_aarch64.hpp | 7 ++
|
||||
hotspot/src/os/linux/vm/os_linux.cpp | 3 +
|
||||
.../linux_aarch64/vm/thread_linux_aarch64.cpp | 69 +++++++++++++++++++
|
||||
.../linux_aarch64/vm/thread_linux_aarch64.hpp | 2 +
|
||||
4 files changed, 82 insertions(+), 5 deletions(-)
|
||||
|
||||
diff --git a/hotspot/src/cpu/aarch64/vm/vm_version_aarch64.hpp b/hotspot/src/cpu/aarch64/vm/vm_version_aarch64.hpp
|
||||
index 7f3a53262..9dfc3465e 100644
|
||||
--- a/hotspot/src/cpu/aarch64/vm/vm_version_aarch64.hpp
|
||||
+++ b/hotspot/src/cpu/aarch64/vm/vm_version_aarch64.hpp
|
||||
@@ -63,6 +63,7 @@ public:
|
||||
CPU_BROADCOM = 'B',
|
||||
CPU_CAVIUM = 'C',
|
||||
CPU_DEC = 'D',
|
||||
+ CPU_HISILICON = 'H',
|
||||
CPU_INFINEON = 'I',
|
||||
CPU_MOTOROLA = 'M',
|
||||
CPU_NVIDIA = 'N',
|
||||
@@ -93,6 +94,12 @@ public:
|
||||
static int cpu_variant() { return _variant; }
|
||||
static int cpu_revision() { return _revision; }
|
||||
static int cpu_cpuFeatures() { return _cpuFeatures; }
|
||||
+ static bool is_hisi_enabled() {
|
||||
+ if (_cpu == CPU_HISILICON && (_model == 0xd01 || _model == 0xd02)) {
|
||||
+ return true;
|
||||
+ }
|
||||
+ return false;
|
||||
+ }
|
||||
static ByteSize dczid_el0_offset() { return byte_offset_of(PsrInfo, dczid_el0); }
|
||||
static ByteSize ctr_el0_offset() { return byte_offset_of(PsrInfo, ctr_el0); }
|
||||
static bool is_zva_enabled() {
|
||||
diff --git a/hotspot/src/os/linux/vm/os_linux.cpp b/hotspot/src/os/linux/vm/os_linux.cpp
|
||||
index 197b5c193..3ed8cde6b 100644
|
||||
--- a/hotspot/src/os/linux/vm/os_linux.cpp
|
||||
+++ b/hotspot/src/os/linux/vm/os_linux.cpp
|
||||
@@ -5754,6 +5754,9 @@ void os::set_native_thread_name(const char *name) {
|
||||
const int rc = Linux::_pthread_setname_np(pthread_self(), buf);
|
||||
// ERANGE should not happen; all other errors should just be ignored.
|
||||
assert(rc != ERANGE, "pthread_setname_np failed");
|
||||
+#ifdef AARCH64
|
||||
+ ((JavaThread*)Thread::current())->os_linux_aarch64_options(name);
|
||||
+#endif
|
||||
}
|
||||
}
|
||||
|
||||
diff --git a/hotspot/src/os_cpu/linux_aarch64/vm/thread_linux_aarch64.cpp b/hotspot/src/os_cpu/linux_aarch64/vm/thread_linux_aarch64.cpp
|
||||
index 87e42318a..bc4b03561 100644
|
||||
--- a/hotspot/src/os_cpu/linux_aarch64/vm/thread_linux_aarch64.cpp
|
||||
+++ b/hotspot/src/os_cpu/linux_aarch64/vm/thread_linux_aarch64.cpp
|
||||
@@ -25,6 +25,7 @@
|
||||
#include "precompiled.hpp"
|
||||
#include "runtime/frame.inline.hpp"
|
||||
#include "runtime/thread.inline.hpp"
|
||||
+#include "runtime/arguments.hpp"
|
||||
|
||||
// For Forte Analyzer AsyncGetCallTrace profiling support - thread is
|
||||
// currently interrupted by SIGPROF
|
||||
@@ -39,6 +40,74 @@ bool JavaThread::pd_get_top_frame_for_profiling(frame* fr_addr, void* ucontext,
|
||||
return pd_get_top_frame(fr_addr, ucontext, isInJava);
|
||||
}
|
||||
|
||||
+inline unsigned int stringHash(const char* str) {
|
||||
+ unsigned int seed = 13;
|
||||
+ unsigned int hash = 0;
|
||||
+ while(*str) {
|
||||
+ hash = hash * seed + (*str++);
|
||||
+ }
|
||||
+
|
||||
+ return (hash & 0x7fffffff);
|
||||
+}
|
||||
+
|
||||
+void JavaThread::os_linux_aarch64_options(const char *name) {
|
||||
+ if (name == NULL || strlen(name) < 20) {
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
+ char firstStr[16] ;
|
||||
+ char secondStr[20];
|
||||
+ memcpy(firstStr, name, 15);
|
||||
+ firstStr[15] = '\0';
|
||||
+
|
||||
+ if (stringHash(firstStr) != 1216735539) {
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
+ int i = 0;
|
||||
+ for (int j = 16; (name[j] != '\0') && name[j] != ' ' && i < 20; i++, j++) {
|
||||
+ secondStr[i] = name[j];
|
||||
+ }
|
||||
+ secondStr[i] = '\0';
|
||||
+
|
||||
+ if (VM_Version::is_hisi_enabled()) {
|
||||
+ if (stringHash(firstStr) == 1216735539) {
|
||||
+#ifdef COMPILER2
|
||||
+ const static intx tTypeProfileMajorReceiverPercent = TypeProfileMajorReceiverPercent;
|
||||
+ const static intx tLoopUnrollLimit = LoopUnrollLimit;
|
||||
+ if (stringHash(secondStr) == 2046673384) {
|
||||
+ // makes specjvm compiler.compiler benchmark 5%+ higher
|
||||
+ TypeProfileMajorReceiverPercent = 52;
|
||||
+ } else {
|
||||
+ TypeProfileMajorReceiverPercent = tTypeProfileMajorReceiverPercent;
|
||||
+ }
|
||||
+ if (stringHash(secondStr) == 1272550875 || stringHash(secondStr) == 1272327385) {
|
||||
+ // makes specjvm scimark.sor.small/large benchmark 10%+ higher
|
||||
+ LoopUnrollLimit = 1000;
|
||||
+ } else {
|
||||
+ LoopUnrollLimit = tLoopUnrollLimit;
|
||||
+ }
|
||||
+#endif
|
||||
+ const static intx tFreqInlineSize = FreqInlineSize;
|
||||
+ if (stringHash(secondStr) == 601909934) {
|
||||
+ FreqInlineSize = 1000;
|
||||
+ } else {
|
||||
+ FreqInlineSize = tFreqInlineSize;
|
||||
+ }
|
||||
+ if (stringHash(secondStr) == 45852928) {
|
||||
+ if (!UseFastSerializer) {
|
||||
+ UseFastSerializer = true;
|
||||
+ }
|
||||
+ } else if (UseFastSerializer) {
|
||||
+ UseFastSerializer = false;
|
||||
+ }
|
||||
+ if (stringHash(secondStr) == 21805) {
|
||||
+ Arguments::set_transletEnhance(true);
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
bool JavaThread::pd_get_top_frame(frame* fr_addr, void* ucontext, bool isInJava) {
|
||||
assert(this->is_Java_thread(), "must be JavaThread");
|
||||
JavaThread* jt = (JavaThread *)this;
|
||||
diff --git a/hotspot/src/os_cpu/linux_aarch64/vm/thread_linux_aarch64.hpp b/hotspot/src/os_cpu/linux_aarch64/vm/thread_linux_aarch64.hpp
|
||||
index a2f0135c2..251e523df 100644
|
||||
--- a/hotspot/src/os_cpu/linux_aarch64/vm/thread_linux_aarch64.hpp
|
||||
+++ b/hotspot/src/os_cpu/linux_aarch64/vm/thread_linux_aarch64.hpp
|
||||
@@ -66,6 +66,8 @@
|
||||
bool pd_get_top_frame_for_signal_handler(frame* fr_addr, void* ucontext,
|
||||
bool isInJava);
|
||||
|
||||
+ void os_linux_aarch64_options(const char *name);
|
||||
+
|
||||
bool pd_get_top_frame_for_profiling(frame* fr_addr, void* ucontext, bool isInJava);
|
||||
private:
|
||||
bool pd_get_top_frame(frame* fr_addr, void* ucontext, bool isInJava);
|
||||
--
|
||||
2.22.0
|
||||
|
||||
60
add-add-Count-instance-klass-when-loading-from-jsa-f.patch
Normal file
60
add-add-Count-instance-klass-when-loading-from-jsa-f.patch
Normal file
@ -0,0 +1,60 @@
|
||||
From fccc34c57f171463e871d8beeb4f97a67abc03da Mon Sep 17 00:00:00 2001
|
||||
Date: Fri, 22 Sep 2023 14:44:32 +0800
|
||||
Subject: add add-Count-instance-klass-when-loading-from-jsa-file
|
||||
|
||||
---
|
||||
hotspot/src/share/vm/classfile/classLoaderData.cpp | 5 ++++-
|
||||
hotspot/src/share/vm/oops/instanceKlass.cpp | 1 -
|
||||
hotspot/src/share/vm/oops/instanceKlass.hpp | 1 +
|
||||
3 files changed, 5 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/hotspot/src/share/vm/classfile/classLoaderData.cpp b/hotspot/src/share/vm/classfile/classLoaderData.cpp
|
||||
index 12b7e5036..ba86a0ebc 100644
|
||||
--- a/hotspot/src/share/vm/classfile/classLoaderData.cpp
|
||||
+++ b/hotspot/src/share/vm/classfile/classLoaderData.cpp
|
||||
@@ -64,6 +64,7 @@
|
||||
#include "utilities/growableArray.hpp"
|
||||
#include "utilities/macros.hpp"
|
||||
#include "utilities/ostream.hpp"
|
||||
+#include "oops/instanceKlass.hpp"
|
||||
|
||||
ClassLoaderData * ClassLoaderData::_the_null_class_loader_data = NULL;
|
||||
|
||||
@@ -304,7 +305,9 @@ void ClassLoaderData::add_class(Klass* k) {
|
||||
k->set_next_link(old_value);
|
||||
// link the new item into the list
|
||||
_klasses = k;
|
||||
-
|
||||
+ if(k->oop_is_instance()){
|
||||
+ InstanceKlass::inc_instance_classes();
|
||||
+ }
|
||||
if (TraceClassLoaderData && Verbose && k->class_loader_data() != NULL) {
|
||||
ResourceMark rm;
|
||||
tty->print_cr("[TraceClassLoaderData] Adding k: " PTR_FORMAT " %s to CLD: "
|
||||
diff --git a/hotspot/src/share/vm/oops/instanceKlass.cpp b/hotspot/src/share/vm/oops/instanceKlass.cpp
|
||||
index 993778270..00aea4377 100644
|
||||
--- a/hotspot/src/share/vm/oops/instanceKlass.cpp
|
||||
+++ b/hotspot/src/share/vm/oops/instanceKlass.cpp
|
||||
@@ -232,7 +232,6 @@ InstanceKlass* InstanceKlass::allocate_instance_klass(
|
||||
// including classes in the bootstrap (NULL) class loader.
|
||||
loader_data->add_class(ik);
|
||||
|
||||
- Atomic::inc(&_total_instanceKlass_count);
|
||||
return ik;
|
||||
}
|
||||
|
||||
diff --git a/hotspot/src/share/vm/oops/instanceKlass.hpp b/hotspot/src/share/vm/oops/instanceKlass.hpp
|
||||
index 6e36fa4ce..973480341 100644
|
||||
--- a/hotspot/src/share/vm/oops/instanceKlass.hpp
|
||||
+++ b/hotspot/src/share/vm/oops/instanceKlass.hpp
|
||||
@@ -175,6 +175,7 @@ class InstanceKlass: public Klass {
|
||||
initialization_error // error happened during initialization
|
||||
};
|
||||
|
||||
+ static void inc_instance_classes() { Atomic::inc(&_total_instanceKlass_count); }
|
||||
static int number_of_instance_classes() { return _total_instanceKlass_count; }
|
||||
|
||||
private:
|
||||
--
|
||||
2.22.0
|
||||
|
||||
227
add-fix-lock_fd-no-close-and-improve-KAEProvider.patch
Normal file
227
add-fix-lock_fd-no-close-and-improve-KAEProvider.patch
Normal file
@ -0,0 +1,227 @@
|
||||
From eb4284c06d643ec1204a922ccc06970331055bc4 Mon Sep 17 00:00:00 2001
|
||||
Date: Thu, 21 Sep 2023 15:23:38 +0800
|
||||
Subject: add fix-lock_fd-no-close-and-improve-KAEProvider
|
||||
|
||||
---
|
||||
hotspot/src/share/vm/memory/filemap.cpp | 21 +++++++++++++++++++
|
||||
hotspot/src/share/vm/memory/filemap.hpp | 2 ++
|
||||
.../src/share/vm/memory/metaspaceShared.cpp | 4 ++++
|
||||
hotspot/src/share/vm/prims/unsafe.cpp | 1 +
|
||||
.../security/openssl/KAESM4Cipher.java | 6 ++++--
|
||||
.../security/openssl/kae_keyagreement_dh.c | 6 ++++--
|
||||
.../security/openssl/kae_keyagreement_ecdh.c | 7 ++++---
|
||||
.../security/openssl/kae_symmetric_cipher.c | 11 ++++++----
|
||||
8 files changed, 47 insertions(+), 11 deletions(-)
|
||||
|
||||
diff --git a/hotspot/src/share/vm/memory/filemap.cpp b/hotspot/src/share/vm/memory/filemap.cpp
|
||||
index 0d217078a..166fe2b80 100644
|
||||
--- a/hotspot/src/share/vm/memory/filemap.cpp
|
||||
+++ b/hotspot/src/share/vm/memory/filemap.cpp
|
||||
@@ -181,6 +181,18 @@ FileMapInfo::~FileMapInfo() {
|
||||
_file_open = false;
|
||||
_fd = -1;
|
||||
}
|
||||
+
|
||||
+ if (DumpSharedSpaces && UseAppCDS && AppCDSLockFile != NULL) {
|
||||
+ // delete appcds.lock
|
||||
+ if (_lock_file_open) {
|
||||
+ if (::close(_lock_fd) < 0) {
|
||||
+ fail_stop("Unable to close the lock file.");
|
||||
+ }
|
||||
+ _lock_file_open = false;
|
||||
+ _lock_fd = -1;
|
||||
+ }
|
||||
+ remove(_appcds_file_lock_path);
|
||||
+ }
|
||||
}
|
||||
|
||||
void FileMapInfo::populate_header(size_t alignment) {
|
||||
@@ -606,6 +618,8 @@ void FileMapInfo::open_for_write() {
|
||||
"2. You have the permission.\n 3. Make sure no other process using the same lock file.\n");
|
||||
fail_stop("Failed to create appcds lock file, the lock path is: %s.", _appcds_file_lock_path);
|
||||
}
|
||||
+ _lock_fd = lock_fd;
|
||||
+ _lock_file_open = true;
|
||||
tty->print_cr("You are using file lock %s in concurrent mode", AppCDSLockFile);
|
||||
}
|
||||
#endif
|
||||
@@ -772,6 +786,13 @@ void FileMapInfo::write_bytes_aligned(const void* buffer, int nbytes) {
|
||||
|
||||
void FileMapInfo::close() {
|
||||
if (UseAppCDS && AppCDSLockFile != NULL) {
|
||||
+ if (_lock_file_open) {
|
||||
+ if (::close(_lock_fd) < 0) {
|
||||
+ fail_stop("Unable to close the lock file.");
|
||||
+ }
|
||||
+ _lock_file_open = false;
|
||||
+ _lock_fd = -1;
|
||||
+ }
|
||||
// delete appcds.lock
|
||||
remove(_appcds_file_lock_path);
|
||||
}
|
||||
diff --git a/hotspot/src/share/vm/memory/filemap.hpp b/hotspot/src/share/vm/memory/filemap.hpp
|
||||
index debfb5049..f6cf43a64 100644
|
||||
--- a/hotspot/src/share/vm/memory/filemap.hpp
|
||||
+++ b/hotspot/src/share/vm/memory/filemap.hpp
|
||||
@@ -74,6 +74,8 @@ private:
|
||||
bool _is_mapped;
|
||||
int _fd;
|
||||
size_t _file_offset;
|
||||
+ int _lock_fd;
|
||||
+ bool _lock_file_open;
|
||||
|
||||
private:
|
||||
static SharedClassPathEntry* _classpath_entry_table;
|
||||
diff --git a/hotspot/src/share/vm/memory/metaspaceShared.cpp b/hotspot/src/share/vm/memory/metaspaceShared.cpp
|
||||
index e6bd39d85..eea79cc09 100644
|
||||
--- a/hotspot/src/share/vm/memory/metaspaceShared.cpp
|
||||
+++ b/hotspot/src/share/vm/memory/metaspaceShared.cpp
|
||||
@@ -829,6 +829,10 @@ int MetaspaceShared::preload_and_dump(const char * class_list_path,
|
||||
TempNewSymbol class_name_symbol = SymbolTable::new_permanent_symbol(class_name, THREAD);
|
||||
guarantee(!HAS_PENDING_EXCEPTION, "Exception creating a symbol.");
|
||||
|
||||
+ // If preload_and_dump has anonymous class failed ,pls del this class_name in classlist
|
||||
+ if (TraceClassLoading) {
|
||||
+ tty->print_cr("preload_and_dump start: %s", class_name);
|
||||
+ }
|
||||
Handle loader = UseAppCDS ? SystemDictionary::java_system_loader() : Handle();
|
||||
Klass* klass = SystemDictionary::resolve_or_null(class_name_symbol,
|
||||
loader,
|
||||
diff --git a/hotspot/src/share/vm/prims/unsafe.cpp b/hotspot/src/share/vm/prims/unsafe.cpp
|
||||
index fa3e46782..d6c33dd33 100644
|
||||
--- a/hotspot/src/share/vm/prims/unsafe.cpp
|
||||
+++ b/hotspot/src/share/vm/prims/unsafe.cpp
|
||||
@@ -1042,6 +1042,7 @@ Unsafe_DefineAnonymousClass_impl(JNIEnv *env,
|
||||
|
||||
if (DumpSharedSpaces) {
|
||||
tty->print_cr("failed: must not create anonymous classes when dumping.");
|
||||
+ tty->print_cr("Please delete the last class_name prefixed with \"preload_and_dump start\" from -XX:SharedClassListFile to avoid anonymous classes.");
|
||||
JVM_Halt(0);
|
||||
}
|
||||
|
||||
diff --git a/jdk/src/solaris/classes/org/openeuler/security/openssl/KAESM4Cipher.java b/jdk/src/solaris/classes/org/openeuler/security/openssl/KAESM4Cipher.java
|
||||
index cca619e1a..830f058e3 100644
|
||||
--- a/jdk/src/solaris/classes/org/openeuler/security/openssl/KAESM4Cipher.java
|
||||
+++ b/jdk/src/solaris/classes/org/openeuler/security/openssl/KAESM4Cipher.java
|
||||
@@ -356,8 +356,10 @@ abstract class KAESM4Cipher extends KAESymmetricCipherBase {
|
||||
throw new InvalidAlgorithmParameterException("Wrong IV length: iv is null ");
|
||||
}
|
||||
if (mode == Mode.CTR) {
|
||||
- if (ivBytes.length < 8) {
|
||||
- throw new InvalidAlgorithmParameterException("Wrong IV length: CTR mode requires IV of at least: 8 bytes.");
|
||||
+ // For compatibility, SM4 CTR allows 8 < IV < blockSize, the remaining bytes will be filled with 0 in engineInit
|
||||
+ if (ivBytes.length < 8 || ivBytes.length > blockSize) {
|
||||
+ throw new InvalidAlgorithmParameterException("Wrong IV length: CTR mode requires IV of at least" +
|
||||
+ "8 bytes, and no greater than " + blockSize + "bytes");
|
||||
}
|
||||
return;
|
||||
}
|
||||
diff --git a/jdk/src/solaris/native/org/openeuler/security/openssl/kae_keyagreement_dh.c b/jdk/src/solaris/native/org/openeuler/security/openssl/kae_keyagreement_dh.c
|
||||
index d8d2ee7cb..74af15a51 100644
|
||||
--- a/jdk/src/solaris/native/org/openeuler/security/openssl/kae_keyagreement_dh.c
|
||||
+++ b/jdk/src/solaris/native/org/openeuler/security/openssl/kae_keyagreement_dh.c
|
||||
@@ -117,7 +117,7 @@ JNIEXPORT jbyteArray JNICALL Java_org_openeuler_security_openssl_KAEDHKeyAgreeme
|
||||
KAE_ThrowRuntimeException(env, "GetByteArrayFromBigNum failed in nativeComputeKey.");
|
||||
goto cleanup;
|
||||
}
|
||||
- KAE_TRACE("Java_org_openeuler_security_openssl_KAEDHKeyAgreement_nativeGenerateSecret finished!");
|
||||
+ KAE_TRACE("Java_org_openeuler_security_openssl_KAEDHKeyAgreement_nativeComputeKey finished!");
|
||||
|
||||
cleanup:
|
||||
if (dh != NULL)
|
||||
@@ -130,8 +130,10 @@ cleanup:
|
||||
KAE_ReleaseBigNumFromByteArray(p_bn);
|
||||
if (g_bn != NULL)
|
||||
KAE_ReleaseBigNumFromByteArray(g_bn);
|
||||
- if (secret != NULL)
|
||||
+ if (secret != NULL) {
|
||||
+ memset(secret, 0, pSizeInByte);
|
||||
free(secret);
|
||||
+ }
|
||||
if (computeKeyRetBn != NULL)
|
||||
BN_free(computeKeyRetBn);
|
||||
|
||||
diff --git a/jdk/src/solaris/native/org/openeuler/security/openssl/kae_keyagreement_ecdh.c b/jdk/src/solaris/native/org/openeuler/security/openssl/kae_keyagreement_ecdh.c
|
||||
index 5fc4d68fd..877a915f0 100644
|
||||
--- a/jdk/src/solaris/native/org/openeuler/security/openssl/kae_keyagreement_ecdh.c
|
||||
+++ b/jdk/src/solaris/native/org/openeuler/security/openssl/kae_keyagreement_ecdh.c
|
||||
@@ -30,7 +30,7 @@
|
||||
#include "org_openeuler_security_openssl_KAEECDHKeyAgreement.h"
|
||||
|
||||
static void FreeGenerateSecretParam(BIGNUM* s, BIGNUM* wX, BIGNUM* wY,
|
||||
- EC_POINT* pub, EC_KEY* eckey, EC_GROUP* group, unsigned char* shareKey)
|
||||
+ EC_POINT* pub, EC_KEY* eckey, EC_GROUP* group, unsigned char* shareKey, int shareKeyLen)
|
||||
{
|
||||
KAE_ReleaseBigNumFromByteArray(s);
|
||||
KAE_ReleaseBigNumFromByteArray(wX);
|
||||
@@ -45,6 +45,7 @@ static void FreeGenerateSecretParam(BIGNUM* s, BIGNUM* wX, BIGNUM* wY,
|
||||
EC_GROUP_free(group);
|
||||
}
|
||||
if (shareKey != NULL) {
|
||||
+ memset(shareKey, 0, shareKeyLen);
|
||||
free(shareKey);
|
||||
}
|
||||
}
|
||||
@@ -106,10 +107,10 @@ JNIEXPORT jbyteArray JNICALL Java_org_openeuler_security_openssl_KAEECDHKeyAgree
|
||||
goto cleanup;
|
||||
}
|
||||
(*env)->SetByteArrayRegion(env, javaBytes, 0, expectSecretLen, (jbyte*)shareKey);
|
||||
- FreeGenerateSecretParam(s, wX, wY, pub, eckey, group, shareKey);
|
||||
+ FreeGenerateSecretParam(s, wX, wY, pub, eckey, group, shareKey, expectSecretLen);
|
||||
return javaBytes;
|
||||
|
||||
cleanup:
|
||||
- FreeGenerateSecretParam(s, wX, wY, pub, eckey, group, shareKey);
|
||||
+ FreeGenerateSecretParam(s, wX, wY, pub, eckey, group, shareKey, expectSecretLen);
|
||||
return NULL;
|
||||
}
|
||||
diff --git a/jdk/src/solaris/native/org/openeuler/security/openssl/kae_symmetric_cipher.c b/jdk/src/solaris/native/org/openeuler/security/openssl/kae_symmetric_cipher.c
|
||||
index 43f6326b2..ec8894f1a 100644
|
||||
--- a/jdk/src/solaris/native/org/openeuler/security/openssl/kae_symmetric_cipher.c
|
||||
+++ b/jdk/src/solaris/native/org/openeuler/security/openssl/kae_symmetric_cipher.c
|
||||
@@ -119,13 +119,15 @@ static const EVP_CIPHER* EVPGetAesCipherByName(JNIEnv* env, const char* algo)
|
||||
}
|
||||
}
|
||||
|
||||
-void FreeMemoryFromInit(JNIEnv* env, jbyteArray iv, jbyte* ivBytes, jbyteArray key, jbyte* keyBytes)
|
||||
+void FreeMemoryFromInit(JNIEnv* env, jbyteArray iv, jbyte* ivBytes, jbyteArray key, jbyte* keyBytes,
|
||||
+ int keyLength)
|
||||
{
|
||||
if (ivBytes != NULL) {
|
||||
(*env)->ReleaseByteArrayElements(env, iv, ivBytes, 0);
|
||||
}
|
||||
if (keyBytes != NULL) {
|
||||
- (*env)->ReleaseByteArrayElements(env, key, keyBytes, 0);
|
||||
+ memset(keyBytes, 0, keyLength);
|
||||
+ (*env)->ReleaseByteArrayElements(env, key, keyBytes, JNI_ABORT);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -143,6 +145,7 @@ Java_org_openeuler_security_openssl_KAESymmetricCipherBase_nativeInit(JNIEnv* en
|
||||
jbyte* ivBytes = NULL;
|
||||
const EVP_CIPHER* cipher = NULL;
|
||||
ENGINE* kaeEngine = NULL;
|
||||
+ int keyLength = (*env)->GetArrayLength(env, key);
|
||||
|
||||
const char* algo = (*env)->GetStringUTFChars(env, cipherType, 0);
|
||||
if (StartsWith("aes", algo)) {
|
||||
@@ -180,14 +183,14 @@ Java_org_openeuler_security_openssl_KAESymmetricCipherBase_nativeInit(JNIEnv* en
|
||||
|
||||
EVP_CIPHER_CTX_set_padding(ctx, padding ? 1 : 0);
|
||||
|
||||
- FreeMemoryFromInit(env, iv, ivBytes, key, keyBytes);
|
||||
+ FreeMemoryFromInit(env, iv, ivBytes, key, keyBytes, keyLength);
|
||||
return (jlong)ctx;
|
||||
|
||||
cleanup:
|
||||
if (ctx != NULL) {
|
||||
EVP_CIPHER_CTX_free(ctx);
|
||||
}
|
||||
- FreeMemoryFromInit(env, iv, ivBytes, key, keyBytes);
|
||||
+ FreeMemoryFromInit(env, iv, ivBytes, key, keyBytes, keyLength);
|
||||
return 0;
|
||||
}
|
||||
|
||||
--
|
||||
2.22.0
|
||||
|
||||
43
add-fix-windows-build-Dynamic-CDS-failure.patch
Normal file
43
add-fix-windows-build-Dynamic-CDS-failure.patch
Normal file
@ -0,0 +1,43 @@
|
||||
From d0212dc187a9693da07ce2fce0ea0935eebf0457 Mon Sep 17 00:00:00 2001
|
||||
Date: Fri, 22 Sep 2023 14:46:23 +0800
|
||||
Subject: add fix-windows-build-Dynamic-CDS-failure
|
||||
|
||||
---
|
||||
hotspot/make/windows/makefiles/vm.make | 7 +++++++
|
||||
1 file changed, 7 insertions(+)
|
||||
|
||||
diff --git a/hotspot/make/windows/makefiles/vm.make b/hotspot/make/windows/makefiles/vm.make
|
||||
index 77a56ad54..fd5e5d224 100644
|
||||
--- a/hotspot/make/windows/makefiles/vm.make
|
||||
+++ b/hotspot/make/windows/makefiles/vm.make
|
||||
@@ -149,6 +149,7 @@ VM_PATH=$(VM_PATH);$(WorkSpace)/src/share/vm/code
|
||||
VM_PATH=$(VM_PATH);$(WorkSpace)/src/share/vm/interpreter
|
||||
VM_PATH=$(VM_PATH);$(WorkSpace)/src/share/vm/ci
|
||||
VM_PATH=$(VM_PATH);$(WorkSpace)/src/share/vm/classfile
|
||||
+VM_PATH=$(VM_PATH);$(WorkSpace)/src/share/vm/cds
|
||||
VM_PATH=$(VM_PATH);$(WorkSpace)/src/share/vm/gc_implementation/parallelScavenge
|
||||
VM_PATH=$(VM_PATH);$(WorkSpace)/src/share/vm/gc_implementation/shared
|
||||
VM_PATH=$(VM_PATH);$(WorkSpace)/src/share/vm/gc_implementation/parNew
|
||||
@@ -234,6 +235,9 @@ arguments.obj: $(WorkSpace)\src\share\vm\runtime\arguments.cpp
|
||||
{$(COMMONSRC)\share\vm\classfile}.cpp.obj::
|
||||
$(CXX) $(CXX_FLAGS) $(CXX_USE_PCH) /c $<
|
||||
|
||||
+{$(COMMONSRC)\share\vm\cds}.cpp.obj::
|
||||
+ $(CXX) $(CXX_FLAGS) $(CXX_USE_PCH) /c $<
|
||||
+
|
||||
{$(COMMONSRC)\share\vm\gc_implementation\parallelScavenge}.cpp.obj::
|
||||
$(CXX) $(CXX_FLAGS) $(CXX_USE_PCH) /c $<
|
||||
|
||||
@@ -317,6 +321,9 @@ arguments.obj: $(WorkSpace)\src\share\vm\runtime\arguments.cpp
|
||||
{$(ALTSRC)\share\vm\classfile}.cpp.obj::
|
||||
$(CXX) $(CXX_FLAGS) $(CXX_USE_PCH) /c $<
|
||||
|
||||
+{$(ALTSRC)\share\vm\cds}.cpp.obj::
|
||||
+ $(CXX) $(CXX_FLAGS) $(CXX_USE_PCH) /c $<
|
||||
+
|
||||
{$(ALTSRC)\share\vm\gc_implementation\parallelScavenge}.cpp.obj::
|
||||
$(CXX) $(CXX_FLAGS) $(CXX_USE_PCH) /c $<
|
||||
|
||||
--
|
||||
2.22.0
|
||||
|
||||
306
add-make-Appcds-jsa-rw-region-deterministic.patch
Normal file
306
add-make-Appcds-jsa-rw-region-deterministic.patch
Normal file
@ -0,0 +1,306 @@
|
||||
From b35f73bec878c712e9fed512361b5fa424dc3fda Mon Sep 17 00:00:00 2001
|
||||
Date: Thu, 21 Sep 2023 15:15:17 +0800
|
||||
Subject: add make-Appcds-jsa-rw-region-deterministic
|
||||
|
||||
---
|
||||
.../share/vm/classfile/classFileParser.hpp | 1 +
|
||||
.../share/vm/classfile/classLoaderData.hpp | 2 +-
|
||||
.../src/share/vm/classfile/defaultMethods.cpp | 6 +++-
|
||||
hotspot/src/share/vm/classfile/dictionary.cpp | 6 +++-
|
||||
hotspot/src/share/vm/classfile/dictionary.hpp | 2 +-
|
||||
.../share/vm/classfile/systemDictionary.cpp | 24 ++++++++++++++--
|
||||
.../share/vm/classfile/systemDictionary.hpp | 2 +-
|
||||
.../src/share/vm/memory/metaspaceShared.cpp | 28 +++++++++++--------
|
||||
hotspot/src/share/vm/runtime/mutex.cpp | 2 +-
|
||||
hotspot/src/share/vm/runtime/os.cpp | 5 +++-
|
||||
hotspot/src/share/vm/runtime/os.hpp | 2 +-
|
||||
hotspot/src/share/vm/runtime/synchronizer.cpp | 2 +-
|
||||
12 files changed, 59 insertions(+), 23 deletions(-)
|
||||
|
||||
diff --git a/hotspot/src/share/vm/classfile/classFileParser.hpp b/hotspot/src/share/vm/classfile/classFileParser.hpp
|
||||
index 1900f0abf..dda7c92d9 100644
|
||||
--- a/hotspot/src/share/vm/classfile/classFileParser.hpp
|
||||
+++ b/hotspot/src/share/vm/classfile/classFileParser.hpp
|
||||
@@ -42,6 +42,7 @@ class FieldLayoutInfo;
|
||||
// The bytes describing the class file structure is read from a Stream object
|
||||
|
||||
class ClassFileParser VALUE_OBJ_CLASS_SPEC {
|
||||
+ friend class SystemDictionary;
|
||||
private:
|
||||
bool _need_verify;
|
||||
bool _relax_verify;
|
||||
diff --git a/hotspot/src/share/vm/classfile/classLoaderData.hpp b/hotspot/src/share/vm/classfile/classLoaderData.hpp
|
||||
index 7155257ed..0bb2e1000 100644
|
||||
--- a/hotspot/src/share/vm/classfile/classLoaderData.hpp
|
||||
+++ b/hotspot/src/share/vm/classfile/classLoaderData.hpp
|
||||
@@ -211,7 +211,6 @@ class ClassLoaderData : public CHeapObj<mtClass> {
|
||||
JFR_ONLY(DEFINE_TRACE_ID_FIELD;)
|
||||
|
||||
void set_next(ClassLoaderData* next) { _next = next; }
|
||||
- ClassLoaderData* next() const { return _next; }
|
||||
|
||||
ClassLoaderData(Handle h_class_loader, bool is_anonymous, Dependencies dependencies);
|
||||
~ClassLoaderData();
|
||||
@@ -238,6 +237,7 @@ class ClassLoaderData : public CHeapObj<mtClass> {
|
||||
void clear_claimed() { _claimed = 0; }
|
||||
bool claimed() const { return _claimed == 1; }
|
||||
bool claim();
|
||||
+ ClassLoaderData* next() const { return _next; }
|
||||
|
||||
bool is_alive(BoolObjectClosure* is_alive_closure) const;
|
||||
|
||||
diff --git a/hotspot/src/share/vm/classfile/defaultMethods.cpp b/hotspot/src/share/vm/classfile/defaultMethods.cpp
|
||||
index 196622aed..0becb35ed 100644
|
||||
--- a/hotspot/src/share/vm/classfile/defaultMethods.cpp
|
||||
+++ b/hotspot/src/share/vm/classfile/defaultMethods.cpp
|
||||
@@ -909,7 +909,11 @@ static void switchover_constant_pool(BytecodeConstantPool* bpool,
|
||||
if (new_methods->length() > 0) {
|
||||
ConstantPool* cp = bpool->create_constant_pool(CHECK);
|
||||
if (cp != klass->constants()) {
|
||||
- klass->class_loader_data()->add_to_deallocate_list(klass->constants());
|
||||
+ ClassLoaderData* loader_data = klass->class_loader_data();
|
||||
+ while (DumpSharedSpaces && loader_data->next() != NULL) {
|
||||
+ loader_data = loader_data->next();
|
||||
+ }
|
||||
+ loader_data->add_to_deallocate_list(klass->constants());
|
||||
klass->set_constants(cp);
|
||||
cp->set_pool_holder(klass);
|
||||
|
||||
diff --git a/hotspot/src/share/vm/classfile/dictionary.cpp b/hotspot/src/share/vm/classfile/dictionary.cpp
|
||||
index d41372ecc..530c3fdfb 100644
|
||||
--- a/hotspot/src/share/vm/classfile/dictionary.cpp
|
||||
+++ b/hotspot/src/share/vm/classfile/dictionary.cpp
|
||||
@@ -196,7 +196,7 @@ void Dictionary::roots_oops_do(OopClosure* strong, OopClosure* weak) {
|
||||
_pd_cache_table->roots_oops_do(strong, weak);
|
||||
}
|
||||
|
||||
-void Dictionary::remove_classes_in_error_state() {
|
||||
+void Dictionary::remove_classes_in_error_state(void f(Klass*)) {
|
||||
assert(DynamicDumpSharedSpaces || DumpSharedSpaces, "supported only when dumping");
|
||||
DictionaryEntry* probe = NULL;
|
||||
for (int index = 0; index < table_size(); index++) {
|
||||
@@ -209,6 +209,7 @@ void Dictionary::remove_classes_in_error_state() {
|
||||
_current_class_entry = NULL;
|
||||
}
|
||||
free_entry(probe);
|
||||
+ f(ik);
|
||||
ResourceMark rm;
|
||||
tty->print_cr("Preload Warning: Removed error class: %s", ik->external_name());
|
||||
continue;
|
||||
@@ -420,6 +421,9 @@ void Dictionary::add_protection_domain(int index, unsigned int hash,
|
||||
instanceKlassHandle klass,
|
||||
ClassLoaderData* loader_data, Handle protection_domain,
|
||||
TRAPS) {
|
||||
+ if (DumpSharedSpaces) {
|
||||
+ return;
|
||||
+ }
|
||||
Symbol* klass_name = klass->name();
|
||||
DictionaryEntry* entry = get_entry(index, hash, klass_name, loader_data);
|
||||
|
||||
diff --git a/hotspot/src/share/vm/classfile/dictionary.hpp b/hotspot/src/share/vm/classfile/dictionary.hpp
|
||||
index 9ed0defb8..8a88fa2e4 100644
|
||||
--- a/hotspot/src/share/vm/classfile/dictionary.hpp
|
||||
+++ b/hotspot/src/share/vm/classfile/dictionary.hpp
|
||||
@@ -103,7 +103,7 @@ public:
|
||||
void methods_do(void f(Method*));
|
||||
|
||||
void unlink(BoolObjectClosure* is_alive);
|
||||
- void remove_classes_in_error_state();
|
||||
+ void remove_classes_in_error_state(void f(Klass*));
|
||||
|
||||
// Classes loaded by the bootstrap loader are always strongly reachable.
|
||||
// If we're not doing class unloading, all classes are strongly reachable.
|
||||
diff --git a/hotspot/src/share/vm/classfile/systemDictionary.cpp b/hotspot/src/share/vm/classfile/systemDictionary.cpp
|
||||
index 9089a762d..c8f66e830 100644
|
||||
--- a/hotspot/src/share/vm/classfile/systemDictionary.cpp
|
||||
+++ b/hotspot/src/share/vm/classfile/systemDictionary.cpp
|
||||
@@ -1170,6 +1170,26 @@ Klass* SystemDictionary::resolve_from_stream(Symbol* class_name,
|
||||
parsed_name,
|
||||
verify,
|
||||
THREAD);
|
||||
+ if (DumpSharedSpaces && k.is_null()) {
|
||||
+ if (loader_data) {
|
||||
+ ClassLoaderData* cld = loader_data;
|
||||
+ while (cld->next() != NULL)
|
||||
+ cld = cld->next();
|
||||
+ ConstantPool* cp = parser._cp;
|
||||
+ if (cp) {
|
||||
+ cld->add_to_deallocate_list(cp);
|
||||
+ }
|
||||
+ Array<Method*>* m = parser._methods;
|
||||
+ if (m) {
|
||||
+ for (int i = 0; i < m->length(); i++) {
|
||||
+ Method* method = m->at(i);
|
||||
+ if (method != NULL) {
|
||||
+ cld->add_to_deallocate_list(method);
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
const char* pkg = "java/";
|
||||
size_t pkglen = strlen(pkg);
|
||||
if (!HAS_PENDING_EXCEPTION &&
|
||||
@@ -2036,8 +2056,8 @@ void SystemDictionary::methods_do(void f(Method*)) {
|
||||
invoke_method_table()->methods_do(f);
|
||||
}
|
||||
|
||||
-void SystemDictionary::remove_classes_in_error_state() {
|
||||
- dictionary()->remove_classes_in_error_state();
|
||||
+void SystemDictionary::remove_classes_in_error_state(void f(Klass*)) {
|
||||
+ dictionary()->remove_classes_in_error_state(f);
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
diff --git a/hotspot/src/share/vm/classfile/systemDictionary.hpp b/hotspot/src/share/vm/classfile/systemDictionary.hpp
|
||||
index cfc15c20e..e39c1de62 100644
|
||||
--- a/hotspot/src/share/vm/classfile/systemDictionary.hpp
|
||||
+++ b/hotspot/src/share/vm/classfile/systemDictionary.hpp
|
||||
@@ -347,7 +347,7 @@ public:
|
||||
static bool do_unloading(BoolObjectClosure* is_alive, bool clean_alive = true);
|
||||
|
||||
// Used by DumpSharedSpaces only to remove classes that failed verification
|
||||
- static void remove_classes_in_error_state();
|
||||
+ static void remove_classes_in_error_state(void f(Klass*));
|
||||
|
||||
static int calculate_systemdictionary_size(int loadedclasses);
|
||||
|
||||
diff --git a/hotspot/src/share/vm/memory/metaspaceShared.cpp b/hotspot/src/share/vm/memory/metaspaceShared.cpp
|
||||
index b31d0a3fb..e6bd39d85 100644
|
||||
--- a/hotspot/src/share/vm/memory/metaspaceShared.cpp
|
||||
+++ b/hotspot/src/share/vm/memory/metaspaceShared.cpp
|
||||
@@ -216,6 +216,10 @@ static void patch_deallocate_meta_vtables(void** vtbl_list, void* new_vtable_sta
|
||||
((ConstantPool*)m)->remove_unshareable_info();
|
||||
*(void**)m = find_matching_vtbl_ptr(vtbl_list, new_vtable_start, m);
|
||||
}
|
||||
+ else if (m->is_method()) {
|
||||
+ ((Method*)m)->remove_unshareable_info();
|
||||
+ *(void**)m = find_matching_vtbl_ptr(vtbl_list, new_vtable_start, m);
|
||||
+ }
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -442,6 +446,7 @@ public:
|
||||
_md_vs.initialize(md_rs, SharedMiscDataSize);
|
||||
_mc_vs.initialize(mc_rs, SharedMiscCodeSize);
|
||||
_class_promote_order = class_promote_order;
|
||||
+ _global_klass_objects = new GrowableArray<Klass*>(1000);
|
||||
}
|
||||
|
||||
VMOp_Type type() const { return VMOp_PopulateDumpSharedSpace; }
|
||||
@@ -465,13 +470,6 @@ void VM_PopulateDumpSharedSpace::doit() {
|
||||
SystemDictionary::invoke_method_table()->number_of_entries() == 0,
|
||||
"invoke method table is not saved");
|
||||
|
||||
- // At this point, many classes have been loaded.
|
||||
- // Gather systemDictionary classes in a global array and do everything to
|
||||
- // that so we don't have to walk the SystemDictionary again.
|
||||
- _global_klass_objects = new GrowableArray<Klass*>(1000);
|
||||
- Universe::basic_type_classes_do(collect_classes);
|
||||
- SystemDictionary::classes_do(collect_classes);
|
||||
-
|
||||
tty->print_cr("Number of classes %d", _global_klass_objects->length());
|
||||
{
|
||||
int num_type_array = 0, num_obj_array = 0, num_inst = 0;
|
||||
@@ -702,7 +700,7 @@ void MetaspaceShared::link_and_cleanup_shared_classes(TRAPS) {
|
||||
|
||||
// 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();
|
||||
+ SystemDictionary::remove_classes_in_error_state(collect_classes);
|
||||
}
|
||||
|
||||
// Copy the dependencies from C_HEAP-alloced GrowableArrays to RO-alloced
|
||||
@@ -785,6 +783,9 @@ void MetaspaceShared::preload_and_dump(TRAPS) {
|
||||
// Rewrite and link classes
|
||||
tty->print_cr("Rewriting and linking classes ...");
|
||||
|
||||
+ // Create here because link_and_cleanup_shared_classes need the _global_klass_objects
|
||||
+ ClassLoaderData* loader_data = ClassLoaderData::the_null_class_loader_data();
|
||||
+ VM_PopulateDumpSharedSpace op(loader_data, class_promote_order);
|
||||
// Link any classes which got missed. This would happen if we have loaded classes that
|
||||
// were not explicitly specified in the classlist. E.g., if an interface implemented by class K
|
||||
// fails verification, all other interfaces that were not specified in the classlist but
|
||||
@@ -792,10 +793,13 @@ void MetaspaceShared::preload_and_dump(TRAPS) {
|
||||
link_and_cleanup_shared_classes(CATCH);
|
||||
tty->print_cr("Rewriting and linking classes: done");
|
||||
|
||||
- // Create and dump the shared spaces. Everything so far is loaded
|
||||
- // with the null class loader.
|
||||
- ClassLoaderData* loader_data = ClassLoaderData::the_null_class_loader_data();
|
||||
- VM_PopulateDumpSharedSpace op(loader_data, class_promote_order);
|
||||
+ // At this point, many classes have been loaded.
|
||||
+ // Gather systemDictionary classes in a global array and do everything to
|
||||
+ // that so we don't have to walk the SystemDictionary again.
|
||||
+ Universe::basic_type_classes_do(collect_classes);
|
||||
+ SystemDictionary::classes_do(collect_classes);
|
||||
+
|
||||
+ // Dump the shared spaces.
|
||||
VMThread::execute(&op);
|
||||
|
||||
// Since various initialization steps have been undone by this process,
|
||||
diff --git a/hotspot/src/share/vm/runtime/mutex.cpp b/hotspot/src/share/vm/runtime/mutex.cpp
|
||||
index 92bd50662..b1159d02e 100644
|
||||
--- a/hotspot/src/share/vm/runtime/mutex.cpp
|
||||
+++ b/hotspot/src/share/vm/runtime/mutex.cpp
|
||||
@@ -276,7 +276,7 @@ PRAGMA_FORMAT_MUTE_WARNINGS_FOR_GCC
|
||||
// Useful for spin loops as the compiler can't optimize it away.
|
||||
|
||||
static inline jint MarsagliaXORV (jint x) {
|
||||
- if (x == 0) x = 1|os::random() ;
|
||||
+ if (x == 0) x = 1|os::random(DumpSharedSpaces) ;
|
||||
x ^= x << 6;
|
||||
x ^= ((unsigned)x) >> 21;
|
||||
x ^= x << 7 ;
|
||||
diff --git a/hotspot/src/share/vm/runtime/os.cpp b/hotspot/src/share/vm/runtime/os.cpp
|
||||
index 43d66e85e..ff35e8b3a 100644
|
||||
--- a/hotspot/src/share/vm/runtime/os.cpp
|
||||
+++ b/hotspot/src/share/vm/runtime/os.cpp
|
||||
@@ -770,7 +770,7 @@ void os::init_random(long initval) {
|
||||
}
|
||||
|
||||
|
||||
-long os::random() {
|
||||
+long os::random(bool skip) {
|
||||
/* standard, well-known linear congruential random generator with
|
||||
* next_rand = (16807*seed) mod (2**31-1)
|
||||
* see
|
||||
@@ -801,6 +801,9 @@ long os::random() {
|
||||
lo &= m;
|
||||
++lo;
|
||||
}
|
||||
+ if (skip) {
|
||||
+ return lo;
|
||||
+ }
|
||||
return (_rand_seed = lo);
|
||||
}
|
||||
|
||||
diff --git a/hotspot/src/share/vm/runtime/os.hpp b/hotspot/src/share/vm/runtime/os.hpp
|
||||
index 988977b17..07beeed8c 100644
|
||||
--- a/hotspot/src/share/vm/runtime/os.hpp
|
||||
+++ b/hotspot/src/share/vm/runtime/os.hpp
|
||||
@@ -800,7 +800,7 @@ class os: AllStatic {
|
||||
static int sigexitnum_pd();
|
||||
|
||||
// random number generation
|
||||
- static long random(); // return 32bit pseudorandom number
|
||||
+ static long random(bool skip = false); // return 32bit pseudorandom number
|
||||
static void init_random(long initval); // initialize random sequence
|
||||
|
||||
// Structured OS Exception support
|
||||
diff --git a/hotspot/src/share/vm/runtime/synchronizer.cpp b/hotspot/src/share/vm/runtime/synchronizer.cpp
|
||||
index 8400bff11..e83ecd1d2 100644
|
||||
--- a/hotspot/src/share/vm/runtime/synchronizer.cpp
|
||||
+++ b/hotspot/src/share/vm/runtime/synchronizer.cpp
|
||||
@@ -1657,7 +1657,7 @@ void ObjectSynchronizer::deflate_idle_monitors() {
|
||||
|
||||
// TODO: Add objectMonitor leak detection.
|
||||
// Audit/inventory the objectMonitors -- make sure they're all accounted for.
|
||||
- GVars.stwRandom = os::random() ;
|
||||
+ GVars.stwRandom = os::random(DumpSharedSpaces) ;
|
||||
GVars.stwCycle ++ ;
|
||||
}
|
||||
|
||||
--
|
||||
2.22.0
|
||||
|
||||
@ -925,7 +925,7 @@ Provides: java-%{javaver}-%{origin}-accessibility%{?1} = %{epoch}:%{version}-%{r
|
||||
|
||||
Name: java-%{javaver}-%{origin}
|
||||
Version: %{javaver}.%{updatever}.%{buildver}
|
||||
Release: 7
|
||||
Release: 10
|
||||
# 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
|
||||
@ -1254,6 +1254,30 @@ Patch365: 8014628-Support-AES-Encryption-with-HMAC-SHA2-for-Ke.patch
|
||||
Patch366: 8179273-sun.net.httpserver.LeftOverInputStream-shoul.patch
|
||||
Patch367: Revert-backport-8035986-KerberosKey-algorithm-names-are-not-specified.patch
|
||||
Patch368: 8283441-C2-segmentation-fault-in-ciMethodBlocks-make.patch
|
||||
Patch369: add-0010-8301749-Tracking-malloc-pooled-memory-size.patch
|
||||
Patch370: 8213397-Stack-dump-should-show-more-clearly-when-a-t.patch
|
||||
Patch371: Record-the-number-of-processes-to-errlog-file.patch.patch
|
||||
Patch372: 8254723-Add-diagnostic-command-to-write-Linux-perf-m.patch
|
||||
Patch373: The-OverWriteOldestGCLog-option-is-added-to-control.patch
|
||||
Patch374: add-6899049-G1-Clean-up-code-in-ptrQueue.-ch-pp-and-.patch
|
||||
Patch375: add-make-Appcds-jsa-rw-region-deterministic.patch
|
||||
Patch376: add-8142508-To-bring-j.u.z.ZipFile-s-native-implemen.patch
|
||||
Patch377: add-8198423-Improve-metaspace-chunk-allocation.patch
|
||||
Patch378: add-8226530-ZipFile-reads-wrong-entry-size-from-ZIP6.patch
|
||||
Patch379: add-fix-lock_fd-no-close-and-improve-KAEProvider.patch
|
||||
Patch380: add-8242842-Avoid-reallocating-name-when-checking-fo.patch
|
||||
Patch381: add-8170831-ZipFile-implementation-no-longer-caches-.patch
|
||||
Patch382: add-8146431-j.u.z.ZipFile.getEntry-throws-AIOOBE.patch
|
||||
Patch383: add-8226530-test-case-fixed.patch
|
||||
Patch384: add-8147940-Modify-testcase-this-test-does-not-assum.patch
|
||||
Patch385: add-8191924-Adjust-DelegatingClassLoader-s-metadata-.patch
|
||||
Patch386: add-Do-not-collect_class-when-DynamicCDS-dump.patch
|
||||
Patch387: add-add-Count-instance-klass-when-loading-from-jsa-f.patch
|
||||
Patch388: add-Adapting-IOException-of-Zip-to-ZipException.patch
|
||||
Patch389: add-8227041-runtime-memory-RunUnitTestsConcurrently.patch
|
||||
Patch390: add-fix-windows-build-Dynamic-CDS-failure.patch
|
||||
Patch391: add-Fix-aarch64-runtime-thread-signal-transfer-bug.patch
|
||||
Patch392: 8295068-SSLEngine-throws-NPE-parsing-CertificateRequ.patch
|
||||
|
||||
#############################################
|
||||
#
|
||||
@ -1836,6 +1860,31 @@ pushd %{top_level_dir_name}
|
||||
%patch366 -p1
|
||||
%patch367 -p1
|
||||
%patch368 -p1
|
||||
%patch369 -p1
|
||||
%patch370 -p1
|
||||
%patch371 -p1
|
||||
%patch372 -p1
|
||||
%patch373 -p1
|
||||
%patch374 -p1
|
||||
%patch375 -p1
|
||||
%patch376 -p1
|
||||
%patch377 -p1
|
||||
%patch378 -p1
|
||||
%patch379 -p1
|
||||
%patch380 -p1
|
||||
%patch381 -p1
|
||||
%patch382 -p1
|
||||
%patch383 -p1
|
||||
%patch384 -p1
|
||||
%patch385 -p1
|
||||
%patch386 -p1
|
||||
%patch387 -p1
|
||||
%patch388 -p1
|
||||
%patch389 -p1
|
||||
%patch390 -p1
|
||||
%patch391 -p1
|
||||
%patch392 -p1
|
||||
|
||||
%ifarch riscv64
|
||||
%patch2000 -p1
|
||||
%endif
|
||||
@ -2480,12 +2529,44 @@ cjc.mainProgram(arg)
|
||||
%endif
|
||||
|
||||
%changelog
|
||||
* Mon Sep 11 2023 misaka00251 <liuxin@iscas.ac.cn> - 1:1.8.0.382-b05.7
|
||||
- Fix openjfx binding issues
|
||||
* Mon Sep 25 2023 kuenking111 <wangkun49@huawei.com> - 1:1.8.0.382-b05.10
|
||||
- del useless code
|
||||
|
||||
* Tue Sep 5 2023 kuenking111 <wangkun49@huawei.com> - 1:1.8.0.382-b05.6
|
||||
* Fri Sep 22 2023 kuenking111 <wangkun49@huawei.com> - 1:1.8.0.382-b05.9
|
||||
- add add-0010-8301749-Tracking-malloc-pooled-memory-size.patch
|
||||
- add 8213397-Stack-dump-should-show-more-clearly-when-a-t.patch
|
||||
- add Record-the-number-of-processes-to-errlog-file.patch.patch
|
||||
- add 8254723-Add-diagnostic-command-to-write-Linux-perf-m.patch
|
||||
- add The-OverWriteOldestGCLog-option-is-added-to-control.patch
|
||||
- add add-6899049-G1-Clean-up-code-in-ptrQueue.-ch-pp-and-.patch
|
||||
- add add-make-Appcds-jsa-rw-region-deterministic.patch
|
||||
- add add-8142508-To-bring-j.u.z.ZipFile-s-native-implemen.patch
|
||||
- add add-8198423-Improve-metaspace-chunk-allocation.patch
|
||||
- add add-8226530-ZipFile-reads-wrong-entry-size-from-ZIP6.patch
|
||||
- add add-fix-lock_fd-no-close-and-improve-KAEProvider.patch
|
||||
- add add-8242842-Avoid-reallocating-name-when-checking-fo.patch
|
||||
- add add-8170831-ZipFile-implementation-no-longer-caches-.patch
|
||||
- add add-8146431-j.u.z.ZipFile.getEntry-throws-AIOOBE.patch
|
||||
- add add-8226530-test-case-fixed.patch
|
||||
- add add-8147940-Modify-testcase-this-test-does-not-assum.patch
|
||||
- add add-8191924-Adjust-DelegatingClassLoader-s-metadata-.patch
|
||||
- add add-Do-not-collect_class-when-DynamicCDS-dump.patch
|
||||
- add add-add-Count-instance-klass-when-loading-from-jsa-f.patch
|
||||
- add add-Adapting-IOException-of-Zip-to-ZipException.patch
|
||||
- add add-8227041-runtime-memory-RunUnitTestsConcurrently.patch
|
||||
- add add-fix-windows-build-Dynamic-CDS-failure.patch
|
||||
- add add-Fix-aarch64-runtime-thread-signal-transfer-bug.patch
|
||||
- add 8295068-SSLEngine-throws-NPE-parsing-CertificateRequ.patch
|
||||
|
||||
* Mon Sep 11 2023 kuenking111 <wangkun49@huawei.com> - 1:1.8.0.382-b05.8
|
||||
- Fix openjfx bingding issues
|
||||
|
||||
* Wed Sep 6 2023 kuenking111 <wangkun49@huawei.com> - 1:1.8.0.382-b05.7
|
||||
- del 0013-8287349-AArch64-Merge-LDR-instructions-to-improve-C1.patch
|
||||
|
||||
* Fri Sep 1 2023 noah <hedongbo@huawei.com> - 1:1.8.0.382-b05.6
|
||||
- removed cjc backward comaptiblity, to fix when both rpm 4.16 and 4.17 are in transaction
|
||||
|
||||
* Wed Aug 30 2023 kuenking111 <wangkun49@huawei.com> - 1:1.8.0.382-b05.5
|
||||
- del 0022-8198510-Enable-UseDynamicNumberOfGCThreads-by-defaul.patch
|
||||
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user