Skip to content

Commit 4052052

Browse files
committed
JVM_getAllEventClasses support
Signed-off-by: Gengchen Tuo <gengchen.tuo@ibm.com>
1 parent f9113a3 commit 4052052

3 files changed

Lines changed: 127 additions & 4 deletions

File tree

runtime/jcl/common/jdk_jfr_internal_JVM_common.cpp

Lines changed: 77 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,7 @@
2323
#include "j9.h"
2424
#include "jni.h"
2525
#include "jclprots.h"
26+
#include "ut_j9jcl.h"
2627

2728
#include "ObjectAccessBarrierAPI.hpp"
2829
#include "VMHelpers.hpp"
@@ -100,10 +101,85 @@ Java_jdk_jfr_internal_JVM_getAllEventClasses(JNIEnv *env, jobject obj)
100101
J9VMThread *currentThread = (J9VMThread*) env;
101102
J9JavaVM *vm = currentThread->javaVM;
102103
J9InternalVMFunctions *vmFuncs = vm->internalVMFunctions;
104+
J9MemoryManagerFunctions *mmFuncs = vm->memoryManagerFunctions;
103105
jobject result = NULL;
104106

105107
vmFuncs->internalEnterVMFromJNI(currentThread);
106-
result = vmFuncs->j9jni_createLocalRef(env, vmFuncs->jvmUpcallTransformArrayToList(currentThread, NULL));
108+
109+
omrthread_monitor_enter(vm->jfrState.typeIDMonitor);
110+
111+
/* First pass: count event classes with valid eventClass pointers across all classloaders. */
112+
UDATA eventCount = 0;
113+
J9ClassLoaderWalkState walkState;
114+
J9ClassLoader *classLoader = vmFuncs->allClassLoadersStartDo(&walkState, vm, 0);
115+
116+
while (NULL != classLoader) {
117+
J9HashTable *typeIDTable = classLoader->typeIDs;
118+
if (NULL != typeIDTable) {
119+
J9HashTableState hashTableState = {0};
120+
J9JFRTypeID *entry = (J9JFRTypeID *)hashTableStartDo(typeIDTable, &hashTableState);
121+
122+
while (NULL != entry) {
123+
if (entry->isEvent && (NULL != entry->eventClass)) {
124+
eventCount += 1;
125+
}
126+
entry = (J9JFRTypeID *)hashTableNextDo(&hashTableState);
127+
}
128+
}
129+
classLoader = vmFuncs->allClassLoadersNextDo(&walkState);
130+
}
131+
vmFuncs->allClassLoadersEndDo(&walkState);
132+
133+
/* Get the Class class and create Class[] array class. */
134+
J9Class *javaLangClass = J9VMJAVALANGCLASS_OR_NULL(vm);
135+
UDATA arrayIndex = 0;
136+
j9array_t classArray = NULL;
137+
138+
J9Class *classArrayClass = javaLangClass->arrayClass;
139+
if (NULL == classArrayClass) {
140+
J9ROMArrayClass *arrayOfObjectsROMClass = (J9ROMArrayClass*)J9ROMIMAGEHEADER_FIRSTCLASS(vm->arrayROMClasses);
141+
classArrayClass = vmFuncs->internalCreateArrayClass(currentThread, arrayOfObjectsROMClass, javaLangClass);
142+
if (NULL == classArrayClass) {
143+
goto done;
144+
}
145+
}
146+
147+
/* Allocate the Class[] array. */
148+
classArray = (j9array_t)mmFuncs->J9AllocateIndexableObject(
149+
currentThread, classArrayClass, (U_32)eventCount, J9_GC_ALLOCATE_OBJECT_NON_INSTRUMENTABLE);
150+
if (NULL == classArray) {
151+
vmFuncs->setNativeOutOfMemoryError(currentThread, 0, 0);
152+
goto done;
153+
}
154+
155+
/* Second pass: populate the array with event classes from all classloaders */
156+
classLoader = vmFuncs->allClassLoadersStartDo(&walkState, vm, 0);
157+
158+
while (NULL != classLoader) {
159+
J9HashTable *typeIDTable = classLoader->typeIDs;
160+
if (NULL != typeIDTable) {
161+
J9HashTableState hashTableState = {0};
162+
J9JFRTypeID *entry = (J9JFRTypeID *)hashTableStartDo(typeIDTable, &hashTableState);
163+
164+
while (NULL != entry) {
165+
if (entry->isEvent && (NULL != entry->eventClass)) {
166+
/* Use the stored eventClass pointer directly */
167+
j9object_t classObject = J9VM_J9CLASS_TO_HEAPCLASS(entry->eventClass);
168+
J9JAVAARRAYOFOBJECT_STORE(currentThread, classArray, arrayIndex, classObject);
169+
arrayIndex += 1;
170+
}
171+
entry = (J9JFRTypeID *)hashTableNextDo(&hashTableState);
172+
}
173+
}
174+
classLoader = vmFuncs->allClassLoadersNextDo(&walkState);
175+
}
176+
vmFuncs->allClassLoadersEndDo(&walkState);
177+
178+
/* Convert array to list and create local ref */
179+
result = vmFuncs->j9jni_createLocalRef(env, vmFuncs->jvmUpcallTransformArrayToList(currentThread, (j9object_t)classArray));
180+
181+
done:
182+
omrthread_monitor_exit(vm->jfrState.typeIDMonitor);
107183
vmFuncs->internalExitVMToJNI(currentThread);
108184

109185
return result;

runtime/oti/j9nonbuilder.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -554,6 +554,8 @@ typedef struct J9JFRTypeID {
554554
jlong id;
555555
struct J9UTF8 *className;
556556
BOOLEAN free;
557+
BOOLEAN isEvent;
558+
struct J9Class *eventClass;
557559
} J9JFRTypeID;
558560

559561
typedef struct J9JFRNetworkUtilization {

runtime/vm/jfr.cpp

Lines changed: 48 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -69,14 +69,15 @@ static int J9THREAD_PROC jfrSamplingThreadProc(void *entryArg);
6969
static void jfrExecutionSampleCallback(J9VMThread *currentThread, IDATA handlerKey, void *userData);
7070
static void jfrThreadCPULoadCallback(J9VMThread *currentThread, IDATA handlerKey, void *userData);
7171
static void jfrCheckJFRCMDLineOptions(J9HookInterface **hook, UDATA eventNum, void *eventData, void *userData);
72-
static jlong getTypeIdImpl(J9VMThread *currentThread, J9ClassLoader *classLoader, J9UTF8 *className, BOOLEAN freeName);
72+
static jlong getTypeIdImpl(J9VMThread *currentThread, J9ClassLoader *classLoader, J9UTF8 *className, BOOLEAN freeName, J9Class *clazz = NULL);
7373
#if JAVA_SPEC_VERSION >= 17
7474
static bool addEventIds(J9JavaVM *vm);
7575
static bool addTypeIds(J9JavaVM *vm);
7676
#endif /* JAVA_SPEC_VERSION >= 17 */
7777
static void jfrShutdownInternalStructures(J9HookInterface **hook, UDATA eventNum, void *eventData, void *userData);
7878
static void notifyForChunkRotation(J9VMThread *currentThread);
7979
static void checkAvailableSpaceInGlobalBuffer(J9VMThread *currentThread);
80+
static void jfrClassInitialize(J9HookInterface **hook, UDATA eventNum, void *eventData, void *userData);
8081

8182
static void
8283
freeThreadIDs(J9VMThread *currentThread)
@@ -1159,6 +1160,7 @@ stopJFRRecording(J9JavaVM *vm)
11591160
(*vmHooks)->J9HookUnregister(vmHooks, J9HOOK_VM_MONITOR_CONTENDED_ENTERED, jfrVMMonitorEntered, NULL);
11601161
(*vmHooks)->J9HookUnregister(vmHooks, J9HOOK_VM_UNPARKED, jfrVMThreadParked, NULL);
11611162
(*vmHooks)->J9HookUnregister(vmHooks, J9HOOK_SYSTEM_GC_CALLED, jfrSystemGC, NULL);
1163+
11621164
/* Deregister GC-related hooks via gc_base */
11631165
vm->memoryManagerFunctions->j9gc_deregister_jfr_hooks(vm);
11641166
}
@@ -1717,13 +1719,25 @@ getTypeId(J9VMThread *currentThread, J9Class *clazz)
17171719
}
17181720

17191721
static jlong
1720-
getTypeIdImpl(J9VMThread *currentThread, J9ClassLoader *classLoader, J9UTF8 *className, BOOLEAN freeName)
1722+
getTypeIdImpl(J9VMThread *currentThread, J9ClassLoader *classLoader, J9UTF8 *className, BOOLEAN freeName, J9Class *clazz)
17211723
{
17221724
J9JavaVM *vm = currentThread->javaVM;
17231725
jlong result = INVALID_TYPE_ID;
17241726
J9JFRTypeID entry = {0};
17251727
J9JFRTypeID *jfrTypeID = &entry;
17261728

1729+
if (NULL != clazz) {
1730+
if (NULL == vm->jfrState.jfrEventClassRef) {
1731+
return -1;
1732+
}
1733+
J9Class *eventClass = J9VMJAVALANGCLASS_VMREF(currentThread, J9_JNI_UNWRAP_REFERENCE(vm->jfrState.jfrEventClassRef));
1734+
if (!isSameOrSuperClassOf(eventClass, clazz)
1735+
|| J9_ARE_NO_BITS_SET(clazz->romClass->modifiers, J9AccAbstract)
1736+
) {
1737+
return -1;
1738+
}
1739+
}
1740+
17271741
Assert_VM_mustHaveVMAccess(currentThread);
17281742

17291743
omrthread_monitor_enter(vm->jfrState.typeIDMonitor);
@@ -1749,7 +1763,6 @@ getTypeIdImpl(J9VMThread *currentThread, J9ClassLoader *classLoader, J9UTF8 *cla
17491763
setNativeOutOfMemoryError(currentThread, 0, 0);
17501764
goto done;
17511765
}
1752-
classLoader->typeIDs = typeIDTable;
17531766

17541767
#if JAVA_SPEC_VERSION >= 17
17551768
if (vm->systemClassLoader == classLoader) {
@@ -1770,6 +1783,8 @@ getTypeIdImpl(J9VMThread *currentThread, J9ClassLoader *classLoader, J9UTF8 *cla
17701783
}
17711784
}
17721785
#endif /* JAVA_SPEC_VERSION >= 17 */
1786+
1787+
classLoader->typeIDs = typeIDTable;
17731788
}
17741789

17751790
jfrTypeID->className = className;
@@ -1780,6 +1795,8 @@ getTypeIdImpl(J9VMThread *currentThread, J9ClassLoader *classLoader, J9UTF8 *cla
17801795
jfrTypeID = &entry;
17811796
jfrTypeID->id = vm->jfrState.typeIDcount;
17821797
jfrTypeID->free = freeName;
1798+
jfrTypeID->isEvent = FALSE;
1799+
jfrTypeID->eventClass = NULL;
17831800

17841801
vm->jfrState.typeIDcount += 1;
17851802
Assert_VM_true(vm->jfrState.typeIDcount > 0);
@@ -1789,6 +1806,9 @@ getTypeIdImpl(J9VMThread *currentThread, J9ClassLoader *classLoader, J9UTF8 *cla
17891806
setNativeOutOfMemoryError(currentThread, 0, 0);
17901807
goto done;
17911808
}
1809+
} else if (NULL != clazz) {
1810+
jfrTypeID->isEvent = TRUE;
1811+
jfrTypeID->eventClass = clazz;
17921812
}
17931813
result = jfrTypeID->id;
17941814

@@ -1812,6 +1832,12 @@ initializeJFRv2(J9JavaVM *vm)
18121832
goto done;
18131833
}
18141834

1835+
if (J9_ARE_ALL_BITS_SET(vm->extendedRuntimeFlags3, J9_EXTENDED_RUNTIME3_JFR_V2_SUPPORT)) {
1836+
if ((*vmHooks)->J9HookRegisterWithCallSite(vmHooks, J9HOOK_VM_CLASS_INITIALIZE, jfrClassInitialize, OMR_GET_CALLSITE(), NULL)) {
1837+
goto done;
1838+
}
1839+
}
1840+
18151841
if (0 != initializeJFRIDs(vm)) {
18161842
goto done;
18171843
}
@@ -1864,7 +1890,13 @@ jfrShutdownInternalStructures(J9HookInterface **hook, UDATA eventNum, void *even
18641890
internalReleaseVMAccess(currentThread);
18651891
vm->jfrState.jfrEventClassRef = NULL;
18661892
vm->jfrState.jfrInternalEventClassRef = NULL;
1893+
<<<<<<< HEAD
18671894
vm->jfrState.chunkRotationMonitor = NULL;
1895+
=======
1896+
if (J9_ARE_ALL_BITS_SET(vm->extendedRuntimeFlags3, J9_EXTENDED_RUNTIME3_JFR_V2_SUPPORT)) {
1897+
(*hook)->J9HookUnregister(hook, J9HOOK_VM_CLASS_INITIALIZE, jfrClassInitialize, NULL);
1898+
}
1899+
>>>>>>> 9d3b593677 (JVM_getAllEventClasses support)
18681900
}
18691901

18701902
static void
@@ -2029,6 +2061,8 @@ addType(J9JavaVM *vm, const char *eventOrTypeName, UDATA id, bool isEvent)
20292061
entry.id = id;
20302062
entry.className = className;
20312063
entry.free = TRUE;
2064+
entry.isEvent = isEvent;
2065+
entry.eventClass = NULL;
20322066

20332067
/* Add to hash table */
20342068
if (NULL == hashTableAdd(typeIDTable, &entry)) {
@@ -2402,6 +2436,17 @@ checkAvailableSpaceInGlobalBuffer(J9VMThread *currentThread)
24022436
}
24032437
}
24042438

2439+
void
2440+
jfrClassInitialize(J9HookInterface **hook, UDATA eventNum, void *eventData, void *userData)
2441+
{
2442+
J9VMClassInitializeEvent *event = (J9VMClassInitializeEvent *)eventData;
2443+
J9VMThread *currentThread = event->currentThread;
2444+
J9Class *clazz = event->clazz;
2445+
2446+
/* getTypeIdImpl will add clazz to the TypeID table. */
2447+
getTypeIdImpl(currentThread, clazz->classLoader, J9ROMCLASS_CLASSNAME(clazz->romClass), FALSE, clazz);
2448+
}
2449+
24052450
} /* extern "C" */
24062451

24072452
#endif /* defined(J9VM_OPT_JFR) */

0 commit comments

Comments
 (0)