8241803: JFR TestThreadStartEndEvents.java failed due to "RuntimeException: Wrong thread id"
Reviewed-by: egahlin
This commit is contained in:
parent
653af300cc
commit
1b3a127d06
@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright (c) 2013, 2018, Oracle and/or its affiliates. All rights reserved.
|
* Copyright (c) 2013, 2020, Oracle and/or its affiliates. All rights reserved.
|
||||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||||
*
|
*
|
||||||
* This code is free software; you can redistribute it and/or modify it
|
* This code is free software; you can redistribute it and/or modify it
|
||||||
@ -48,16 +48,19 @@ import jdk.test.lib.jfr.Events;
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Starts and stops a number of threads in order.
|
* Starts a number of threads in order and verifies
|
||||||
* Verifies that events are in the same order.
|
* that Thread Start events are in that same order.
|
||||||
|
* The order of Thread End events is non-deterministic.
|
||||||
*/
|
*/
|
||||||
public class TestThreadStartEndEvents {
|
public class TestThreadStartEndEvents {
|
||||||
private final static String EVENT_NAME_THREAD_START = EventNames.ThreadStart;
|
private final static String EVENT_NAME_THREAD_START = EventNames.ThreadStart;
|
||||||
private final static String EVENT_NAME_THREAD_END = EventNames.ThreadEnd;
|
private final static String EVENT_NAME_THREAD_END = EventNames.ThreadEnd;
|
||||||
private static final String THREAD_NAME_PREFIX = "TestThread-";
|
private static final String THREAD_NAME_PREFIX = "TestThread-";
|
||||||
|
private static int currentThreadIndex = 0;
|
||||||
|
private static int numberOfThreadStartEvents = 0;
|
||||||
|
private static int numberOfThreadEndEvents = 0;
|
||||||
|
|
||||||
public static void main(String[] args) throws Throwable {
|
public static void main(String[] args) throws Throwable {
|
||||||
// Test Java Thread Start event
|
|
||||||
Recording recording = new Recording();
|
Recording recording = new Recording();
|
||||||
recording.enable(EVENT_NAME_THREAD_START).withThreshold(Duration.ofMillis(0));
|
recording.enable(EVENT_NAME_THREAD_START).withThreshold(Duration.ofMillis(0));
|
||||||
recording.enable(EVENT_NAME_THREAD_END).withThreshold(Duration.ofMillis(0));
|
recording.enable(EVENT_NAME_THREAD_END).withThreshold(Duration.ofMillis(0));
|
||||||
@ -65,8 +68,6 @@ public class TestThreadStartEndEvents {
|
|||||||
LatchedThread[] threads = startThreads();
|
LatchedThread[] threads = startThreads();
|
||||||
stopThreads(threads);
|
stopThreads(threads);
|
||||||
recording.stop();
|
recording.stop();
|
||||||
|
|
||||||
int currThreadIndex = 0;
|
|
||||||
List<RecordedEvent> events = Events.fromRecording(recording);
|
List<RecordedEvent> events = Events.fromRecording(recording);
|
||||||
events.sort((e1, e2) -> e1.getStartTime().compareTo(e2.getStartTime()));
|
events.sort((e1, e2) -> e1.getStartTime().compareTo(e2.getStartTime()));
|
||||||
Events.hasEvents(events);
|
Events.hasEvents(events);
|
||||||
@ -75,22 +76,37 @@ public class TestThreadStartEndEvents {
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
System.out.println("Event:" + event);
|
System.out.println("Event:" + event);
|
||||||
// Threads should be started and stopped in the correct order.
|
String eventType = event.getEventType().getName();
|
||||||
Events.assertEventThread(event, threads[currThreadIndex % threads.length]);
|
switch (eventType) {
|
||||||
String eventName = currThreadIndex < threads.length ? EVENT_NAME_THREAD_START : EVENT_NAME_THREAD_END;
|
case EVENT_NAME_THREAD_START:
|
||||||
if (!eventName.equals(event.getEventType().getName())) {
|
validateThreadStartEvent(event, threads);
|
||||||
throw new Exception("Expected event of type " + eventName + " but got " + event.getEventType().getName());
|
break;
|
||||||
|
case EVENT_NAME_THREAD_END:
|
||||||
|
validateThreadEndEvent(event);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
throw new RuntimeException("Test encountered an invalid event: " + eventType);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (eventName == EVENT_NAME_THREAD_START) {
|
|
||||||
Events.assertEventThread(event, "parentThread", Thread.currentThread());
|
|
||||||
RecordedStackTrace stackTrace = event.getValue("stackTrace");
|
|
||||||
assertNotNull(stackTrace);
|
|
||||||
RecordedMethod topMethod = stackTrace.getFrames().get(0).getMethod();
|
|
||||||
assertEQ(topMethod.getName(), "startThread");
|
|
||||||
}
|
|
||||||
currThreadIndex++;
|
|
||||||
}
|
}
|
||||||
|
assertEQ(numberOfThreadStartEvents, threads.length);
|
||||||
|
assertEQ(numberOfThreadEndEvents, threads.length);
|
||||||
|
}
|
||||||
|
|
||||||
|
// The order of Thread Start events should corresponding to their start order.
|
||||||
|
private static void validateThreadStartEvent(RecordedEvent event, LatchedThread[] threads) {
|
||||||
|
Events.assertEventThread(event, threads[currentThreadIndex++]);
|
||||||
|
Events.assertEventThread(event, "parentThread", Thread.currentThread());
|
||||||
|
RecordedStackTrace stackTrace = event.getValue("stackTrace");
|
||||||
|
assertNotNull(stackTrace);
|
||||||
|
RecordedMethod topMethod = stackTrace.getFrames().get(0).getMethod();
|
||||||
|
assertEQ(topMethod.getName(), "startThread");
|
||||||
|
numberOfThreadStartEvents++;
|
||||||
|
}
|
||||||
|
|
||||||
|
// The order of Thread End events is non-deterministic. This is because the event
|
||||||
|
// is committed as part of dismantling the JavaThread in the VM, post thread.isAlive().
|
||||||
|
private static void validateThreadEndEvent(RecordedEvent event) {
|
||||||
|
numberOfThreadEndEvents++;
|
||||||
}
|
}
|
||||||
|
|
||||||
private static LatchedThread[] startThreads() {
|
private static LatchedThread[] startThreads() {
|
||||||
@ -147,5 +163,4 @@ public class TestThreadStartEndEvents {
|
|||||||
stop.countDown();
|
stop.countDown();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user