Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

8262049: [TESTBUG] Fix TestReferenceRefersTo.java for Shenandoah IU mode #2653

Closed
wants to merge 6 commits into from
Closed
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion test/hotspot/jtreg/gc/TestReferenceRefersTo.java
Original file line number Diff line number Diff line change
@@ -238,7 +238,8 @@ private static void testConcurrentCollection() throws Exception {
fail("testWeak3 notified");
}
if ((testWeak4 == null) != (obj4 == null)) {
fail("either referent is cleared and we got notified, or neither of this happened");
fail("either referent is cleared and we got notified, or neither of this happened: referent: "
+ obj4 + ", notified: " + (testWeak == null));
}

} finally {
97 changes: 9 additions & 88 deletions test/hotspot/jtreg/gc/TestReferenceRefersToDuringConcMark.java
Original file line number Diff line number Diff line change
@@ -24,7 +24,6 @@
package gc;

/* @test
* @requires vm.gc != "Epsilon"
* @requires vm.gc != "Shenandoah"
* @library /test/lib
* @build sun.hotspot.WhiteBox
@@ -36,37 +35,20 @@
* gc.TestReferenceRefersToDuringConcMark
*/

import java.lang.ref.PhantomReference;
import java.lang.ref.Reference;
import java.lang.ref.ReferenceQueue;
import java.lang.ref.WeakReference;
import sun.hotspot.WhiteBox;

public class TestReferenceRefersToDuringConcMark {
private static final WhiteBox WB = WhiteBox.getWhiteBox();

private static final class TestObject {
public final int value;
private static volatile Object testObject = null;

public TestObject(int value) {
this.value = value;
}
}

private static volatile TestObject testObjectNone = null;
private static volatile TestObject testObject = null;

private static ReferenceQueue<TestObject> queue = null;

private static WeakReference<TestObject> testWeak = null;
private static WeakReference<Object> testWeak = null;

private static void setup() {
testObjectNone = new TestObject(0);
testObject = new TestObject(4);

queue = new ReferenceQueue<TestObject>();

testWeak = new WeakReference<TestObject>(testObject, queue);
testObject = new Object();
testWeak = new WeakReference<Object>(testObject);
}

private static void gcUntilOld(Object o) throws Exception {
@@ -79,54 +61,30 @@ private static void gcUntilOld(Object o) throws Exception {
}

private static void gcUntilOld() throws Exception {
gcUntilOld(testObjectNone);
gcUntilOld(testObject);

gcUntilOld(testWeak);
}

private static void progress(String msg) {
System.out.println(msg);
}

private static void fail(String msg) throws Exception {
throw new RuntimeException(msg);
}

private static void expectCleared(Reference<TestObject> ref,
String which) throws Exception {
expectNotValue(ref, testObjectNone, which);
if (!ref.refersTo(null)) {
fail("expected " + which + " to be cleared");
}
}

private static void expectNotCleared(Reference<TestObject> ref,
private static void expectNotCleared(Reference<Object> ref,
String which) throws Exception {
expectNotValue(ref, testObjectNone, which);
if (ref.refersTo(null)) {
fail("expected " + which + " to not be cleared");
}
}

private static void expectValue(Reference<TestObject> ref,
TestObject value,
private static void expectValue(Reference<Object> ref,
Object value,
String which) throws Exception {
expectNotValue(ref, testObjectNone, which);
expectNotCleared(ref, which);
if (!ref.refersTo(value)) {
fail(which + " doesn't refer to expected value");
}
}

private static void expectNotValue(Reference<TestObject> ref,
TestObject value,
String which) throws Exception {
if (ref.refersTo(value)) {
fail(which + " refers to unexpected value");
}
}

private static void checkInitialStates() throws Exception {
expectValue(testWeak, testObject, "testWeak");
}
@@ -136,66 +94,29 @@ private static void discardStrongReferences() {
}

private static void testConcurrentCollection() throws Exception {
progress("setup concurrent collection test");
setup();
progress("gcUntilOld");
gcUntilOld();

progress("acquire control of concurrent cycles");
WB.concurrentGCAcquireControl();
try {
progress("check initial states");
checkInitialStates();

progress("discard strong references");
discardStrongReferences();

progress("run GC to before marking completed");
WB.concurrentGCRunTo(WB.BEFORE_MARKING_COMPLETED);

progress("fetch test objects, possibly keeping some alive");
// For some collectors, calling get() will keep testObject alive.
// For most collectors - the configurations tested here -,
// calling get() will keep testObject alive.
if (testWeak.get() == null) {
fail("testWeak unexpectedly == null");
}

progress("finish collection");
WB.concurrentGCRunToIdle();

progress("verify expected clears");
expectNotCleared(testWeak, "testWeak");

progress("verify get returns expected values");
TestObject obj = testWeak.get();
if (obj == null) {
fail("testWeak.get() returned null");
} else if (obj.value != 4) {
fail("testWeak.get().value is " + obj.value);
}

progress("verify queue entries");
long timeout = 60000; // 1 minute of milliseconds.
while (true) {
Reference<? extends TestObject> ref = queue.remove(timeout);
if (ref == null) {
break;
} else if (ref == testWeak) {
testWeak = null;
} else {
fail("unexpected reference in queue");
}
}
if (testWeak == null) {
if (obj != null) {
fail("testWeak notified");
}
}

} finally {
progress("release control of concurrent cycles");
WB.concurrentGCReleaseControl();
}
progress("finished concurrent collection test");
}

public static void main(String[] args) throws Exception {