java-11-openjdk/rh1648995-shenandoah_array_copy_broken_by_not_always_copy_forward_for_disjoint_arrays.patch
Jiri Vanek 8063e9fa0c fixed tck failures of arraycopy and process exec with shenandoah on
added patch585 rh1648995-shenandoah_array_copy_broken_by_not_always_copy_forward_for_disjoint_arrays.patch
2018-11-13 14:29:09 +01:00

199 lines
9.4 KiB
Diff

# HG changeset patch
# User zgu
# Date 1541803086 18000
# Node ID 9c4bf4a86cd89f33bee1e372fd8f6071636b0953
# Parent 1e4229c1a99bdbe79e202a41a046c13b9b4bd0b6
[backport] Always copy forward for disjoint arrays
diff -r 1e4229c1a99b -r 9c4bf4a86cd8 src/hotspot/share/gc/shenandoah/shenandoahBarrierSet.hpp
--- a/src/hotspot/share/gc/shenandoah/shenandoahBarrierSet.hpp Fri Nov 09 12:49:43 2018 +0100
+++ b/src/hotspot/share/gc/shenandoah/shenandoahBarrierSet.hpp Fri Nov 09 17:38:06 2018 -0500
@@ -120,18 +120,18 @@
template <typename T>
bool arraycopy_loop_1(T* src, T* dst, size_t length, Klass* bound,
- bool checkcast, bool satb, ShenandoahBarrierSet::ArrayCopyStoreValMode storeval_mode);
+ bool checkcast, bool satb, bool disjoint, ShenandoahBarrierSet::ArrayCopyStoreValMode storeval_mode);
template <typename T, bool CHECKCAST>
bool arraycopy_loop_2(T* src, T* dst, size_t length, Klass* bound,
- bool satb, ShenandoahBarrierSet::ArrayCopyStoreValMode storeval_mode);
+ bool satb, bool disjoint, ShenandoahBarrierSet::ArrayCopyStoreValMode storeval_mode);
template <typename T, bool CHECKCAST, bool SATB>
bool arraycopy_loop_3(T* src, T* dst, size_t length, Klass* bound,
- ShenandoahBarrierSet::ArrayCopyStoreValMode storeval_mode);
+ bool disjoint, ShenandoahBarrierSet::ArrayCopyStoreValMode storeval_mode);
template <typename T, bool CHECKCAST, bool SATB, ShenandoahBarrierSet::ArrayCopyStoreValMode STOREVAL_MODE>
- bool arraycopy_loop(T* src, T* dst, size_t length, Klass* bound);
+ bool arraycopy_loop(T* src, T* dst, size_t length, Klass* bound, bool disjoint);
template <typename T, bool CHECKCAST, bool SATB, ShenandoahBarrierSet::ArrayCopyStoreValMode STOREVAL_MODE>
bool arraycopy_element(T* cur_src, T* cur_dst, Klass* bound, Thread* thread);
diff -r 1e4229c1a99b -r 9c4bf4a86cd8 src/hotspot/share/gc/shenandoah/shenandoahBarrierSet.inline.hpp
--- a/src/hotspot/share/gc/shenandoah/shenandoahBarrierSet.inline.hpp Fri Nov 09 12:49:43 2018 +0100
+++ b/src/hotspot/share/gc/shenandoah/shenandoahBarrierSet.inline.hpp Fri Nov 09 17:38:06 2018 -0500
@@ -93,34 +93,36 @@
template <typename T>
bool ShenandoahBarrierSet::arraycopy_loop_1(T* src, T* dst, size_t length, Klass* bound,
- bool checkcast, bool satb, ShenandoahBarrierSet::ArrayCopyStoreValMode storeval_mode) {
+ bool checkcast, bool satb, bool disjoint,
+ ShenandoahBarrierSet::ArrayCopyStoreValMode storeval_mode) {
if (checkcast) {
- return arraycopy_loop_2<T, true>(src, dst, length, bound, satb, storeval_mode);
+ return arraycopy_loop_2<T, true>(src, dst, length, bound, satb, disjoint, storeval_mode);
} else {
- return arraycopy_loop_2<T, false>(src, dst, length, bound, satb, storeval_mode);
+ return arraycopy_loop_2<T, false>(src, dst, length, bound, satb, disjoint, storeval_mode);
}
}
template <typename T, bool CHECKCAST>
bool ShenandoahBarrierSet::arraycopy_loop_2(T* src, T* dst, size_t length, Klass* bound,
- bool satb, ShenandoahBarrierSet::ArrayCopyStoreValMode storeval_mode) {
+ bool satb, bool disjoint,
+ ShenandoahBarrierSet::ArrayCopyStoreValMode storeval_mode) {
if (satb) {
- return arraycopy_loop_3<T, CHECKCAST, true>(src, dst, length, bound, storeval_mode);
+ return arraycopy_loop_3<T, CHECKCAST, true>(src, dst, length, bound, disjoint, storeval_mode);
} else {
- return arraycopy_loop_3<T, CHECKCAST, false>(src, dst, length, bound, storeval_mode);
+ return arraycopy_loop_3<T, CHECKCAST, false>(src, dst, length, bound, disjoint, storeval_mode);
}
}
template <typename T, bool CHECKCAST, bool SATB>
-bool ShenandoahBarrierSet::arraycopy_loop_3(T* src, T* dst, size_t length, Klass* bound,
+bool ShenandoahBarrierSet::arraycopy_loop_3(T* src, T* dst, size_t length, Klass* bound, bool disjoint,
ShenandoahBarrierSet::ArrayCopyStoreValMode storeval_mode) {
switch (storeval_mode) {
case NONE:
- return arraycopy_loop<T, CHECKCAST, SATB, NONE>(src, dst, length, bound);
+ return arraycopy_loop<T, CHECKCAST, SATB, NONE>(src, dst, length, bound, disjoint);
case READ_BARRIER:
- return arraycopy_loop<T, CHECKCAST, SATB, READ_BARRIER>(src, dst, length, bound);
+ return arraycopy_loop<T, CHECKCAST, SATB, READ_BARRIER>(src, dst, length, bound, disjoint);
case WRITE_BARRIER:
- return arraycopy_loop<T, CHECKCAST, SATB, WRITE_BARRIER>(src, dst, length, bound);
+ return arraycopy_loop<T, CHECKCAST, SATB, WRITE_BARRIER>(src, dst, length, bound, disjoint);
default:
ShouldNotReachHere();
return true; // happy compiler
@@ -128,30 +130,30 @@
}
template <typename T, bool CHECKCAST, bool SATB, ShenandoahBarrierSet::ArrayCopyStoreValMode STOREVAL_MODE>
-bool ShenandoahBarrierSet::arraycopy_loop(T* src, T* dst, size_t length, Klass* bound) {
+bool ShenandoahBarrierSet::arraycopy_loop(T* src, T* dst, size_t length, Klass* bound, bool disjoint) {
Thread* thread = Thread::current();
ShenandoahEvacOOMScope oom_evac_scope;
// We need to handle four cases:
//
- // a) src < dst, intersecting, can only copy backward only
+ // a) src < dst, conjoint, can only copy backward only
// [...src...]
// [...dst...]
//
- // b) src < dst, non-intersecting, can copy forward/backward
+ // b) src < dst, disjoint, can only copy forward, because types may mismatch
// [...src...]
// [...dst...]
//
- // c) src > dst, intersecting, can copy forward only
+ // c) src > dst, conjoint, can copy forward only
// [...src...]
// [...dst...]
//
- // d) src > dst, non-intersecting, can copy forward/backward
+ // d) src > dst, disjoint, can only copy forward, because types may mismatch
// [...src...]
// [...dst...]
//
- if (src > dst) {
+ if (src > dst || disjoint) {
// copy forward:
T* cur_src = src;
T* cur_dst = dst;
@@ -248,6 +250,7 @@
bool satb = ShenandoahSATBBarrier && heap->is_concurrent_mark_in_progress();
bool checkcast = HasDecorator<decorators, ARRAYCOPY_CHECKCAST>::value;
+ bool disjoint = HasDecorator<decorators, ARRAYCOPY_DISJOINT>::value;
ArrayCopyStoreValMode storeval_mode;
if (heap->has_forwarded_objects()) {
if (heap->is_concurrent_traversal_in_progress()) {
@@ -273,7 +276,7 @@
Klass* bound = objArrayOop(dst_obj)->element_klass();
ShenandoahBarrierSet* bs = ShenandoahBarrierSet::barrier_set();
- return bs->arraycopy_loop_1(src_raw, dst_raw, length, bound, checkcast, satb, storeval_mode);
+ return bs->arraycopy_loop_1(src_raw, dst_raw, length, bound, checkcast, satb, disjoint, storeval_mode);
}
#endif //SHARE_VM_GC_SHENANDOAH_SHENANDOAHBARRIERSET_INLINE_HPP
diff -r 1e4229c1a99b -r 9c4bf4a86cd8 test/hotspot/jtreg/gc/shenandoah/WrongArrayMember.java
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/test/hotspot/jtreg/gc/shenandoah/WrongArrayMember.java Fri Nov 09 17:38:06 2018 -0500
@@ -0,0 +1,55 @@
+/*
+ * Copyright (c) 2018, Red Hat, Inc. and/or its affiliates.
+ *
+ * This code is free software; you can redistribute 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 WrongArrayMember
+ *
+ * @run main/othervm -Xmx128m -XX:+UnlockExperimentalVMOptions -XX:+UseShenandoahGC WrongArrayMember
+ * @run main/othervm -Xmx128m -XX:+UnlockExperimentalVMOptions -XX:+UseShenandoahGC -XX:ShenandoahGCHeuristics=traversal WrongArrayMember
+ */
+
+public class WrongArrayMember {
+ public static void main(String... args) throws Exception {
+ Object[] src = new Object[3];
+ src[0] = new Integer(0);
+ src[1] = new Object();
+ src[2] = new Object();
+ Object[] dst = new Integer[3];
+ dst[0] = new Integer(1);
+ dst[1] = new Integer(2);
+ dst[2] = new Integer(3);
+ try {
+ System.arraycopy(src, 0, dst, 0, 3);
+ throw new RuntimeException("Expected ArrayStoreException");
+ } catch (ArrayStoreException e) {
+ if (src[0] != dst[0]) {
+ throw new RuntimeException("First element not copied");
+ } else if (src[1] == dst[1] || src[2] == dst[2]) {
+ throw new RuntimeException("Second and third elements are affected");
+ } else {
+ return; // Passed!
+ }
+ }
+ }
+}
+