Skip to content

Add JFR NativeLibrary event #21629

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

Open
wants to merge 1 commit into
base: master
Choose a base branch
from

Conversation

AditiS11
Copy link

@AditiS11 AditiS11 commented Apr 11, 2025

Add NativeLibrary event to JFR
Capture libraryName, base and top addresses for each library

@AditiS11 AditiS11 force-pushed the nativelibJFRChunk branch from 5619c41 to 1467092 Compare April 11, 2025 18:54
PORT_ACCESS_FROM_VMC(currentThread);;
OMRPORT_ACCESS_FROM_J9PORT(PORTLIB);
this->_nativeLibrariesCount = 0;
uintptr_t result = omrsl_get_libraries(&VM_JFRConstantPoolTypes::tempCallback, this);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

why not pass processNativeLibrariesCallback directly

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I am getting a mismatch error if I pass processNativeLibrariesCallback directly. I need to make the callback static. But if I make the callback static, I won't be able to access the non-static members of the VM_JFRConstantPoolTypes class without creating an object of the class.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Which "non-static members" do you need? you are passing an instance of VM_JFRConstantPoolTypes as a parameter, so you can access non-statics via the getters.

@@ -1246,6 +1268,67 @@ class VM_JFRConstantPoolTypes {
gcConfiguration->heapAddressBits = J9JAVAVM_REFERENCE_SIZE(vm) * 8;
}

uintptr_t processNativeLibrariesCallback(const char *libraryName, void *lowAddress, void *highAddress, void *userData)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this should be a static function

@@ -1246,6 +1268,67 @@ class VM_JFRConstantPoolTypes {
gcConfiguration->heapAddressBits = J9JAVAVM_REFERENCE_SIZE(vm) * 8;
}

uintptr_t processNativeLibrariesCallback(const char *libraryName, void *lowAddress, void *highAddress, void *userData)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

you should add a _nativeLibraryCMDlineStrSizeTotal and += strlen(libraryName) to track the size of the strings, that way you can get a more accurate requiredBufferSize

@tajila tajila self-requested a review April 11, 2025 19:06
@tajila
Copy link
Contributor

tajila commented Apr 11, 2025

Please add a new test case to jfr_events.xml just to validate the event is emitted. You dont need to validate the actual values since those will always change.

_bufferWriter->writeLEB128(entry->ticks);

/* write library name */
_writer->writeStringLiteral(entry->name);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

you can free and NULL the string after you write it to the chunk

@AditiS11 AditiS11 force-pushed the nativelibJFRChunk branch 4 times, most recently from 27136b7 to 775f8c8 Compare April 14, 2025 14:56
/* write event size */
_writer->writeEventSize(_bufferWriter, dataStart);

if (NULL != entry->name)
Copy link
Contributor

@tajila tajila Apr 14, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

NULL check not needed as free() doesn the NULL check

PORT_ACCESS_FROM_JAVAVM(constantPoolTypes->_vm);
while (NULL != entry)
{
if (strcmp(entry->name, libraryName) == 0) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

lvalue should be on the left side of the ==

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Tobi means rvalue (i.e. 0).

if (NULL == strstr(libraryName, ".so")) {
return 0;
}
VM_JFRConstantPoolTypes *constantPoolTypes = static_cast<VM_JFRConstantPoolTypes *>(userData);
Copy link
Contributor

@tajila tajila Apr 14, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

should be a reinterpret cast

}
entry = entry->next;
}
NativeLibraryEntry *newEntry = static_cast<NativeLibraryEntry *>(pool_newElement(nativeLibrariesTable));
Copy link
Contributor

@tajila tajila Apr 14, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

should be a reinterpret cast

constantPoolTypes->_nativeLibraryCMDlineStrSizeTotal += strlen(libraryName);
if (previousNativeLibraryEntry != NULL) {
previousNativeLibraryEntry->next = newEntry;
}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

formatting } else {


void loadNativeLibraries(J9VMThread *currentThread)
{
PORT_ACCESS_FROM_VMC(currentThread);;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

double ;;

OMRPORT_ACCESS_FROM_J9PORT(PORTLIB);
this->_nativeLibrariesCount = 0;
uintptr_t result = omrsl_get_libraries(processNativeLibrariesCallback, this);
if (0 != result) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

if result fails you need to set _buildResult to one of the failures.

NativeLibraryEntry *previousNativeLibraryEntry = constantPoolTypes->_previousNativeLibraryEntry;
NativeLibraryEntry *entry = firstNativeLibraryEntry;
PORT_ACCESS_FROM_JAVAVM(constantPoolTypes->_vm);
while (NULL != entry)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

formatting while (cond) {

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggest using a for loop:

		for (; NULL != entry; entry = entry->next) {
...
		}

@@ -1439,6 +1529,14 @@ class VM_JFRConstantPoolTypes {
goto done;
}

_nativeLibrariesTable = pool_new(sizeof(NativeLibraryEntry), 0, sizeof(U_64), 0, J9_GET_CALLSITE(), OMRMEM_CATEGORY_VM, POOL_FOR_PORT(privatePortLibrary));
if(NULL == _nativeLibrariesTable ) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

missing space if (cond) {

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No space before ).

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If you could fix lines 1516, 1522 and 1528 as well, that would be appreciated.

this->_nativeLibrariesCount = 0;
uintptr_t result = omrsl_get_libraries(processNativeLibrariesCallback, this);
if (0 != result) {
return ;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

return is not needed

@keithc-ca keithc-ca self-requested a review April 14, 2025 18:54
Copy link
Contributor

@keithc-ca keithc-ca left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please adjust the commit message: the summary line should not end with a period and I don't think "event" should be capitalized.

VM_JFRChunkWriter::writeNativeLibraryEvent(void *anElement, void *userData)
{
NativeLibraryEntry *entry = (NativeLibraryEntry *)anElement;
VM_JFRChunkWriter *_writer = (VM_JFRChunkWriter *)userData;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please don't use the field naming convention for locals (remove the _ prefix).

@@ -100,6 +100,7 @@ enum MetadataTypeID {
StackTraceID = 188,
FrameTypeID = 189,
StackFrameID = 197,
NativeLibraryID = 112,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please keep this list organized by value.

@@ -899,6 +904,8 @@ class VM_JFRChunkWriter {

requiredBufferSize += _vm->peakThreadCount * THREAD_DUMP_EVENT_SIZE_PER_THREAD;

requiredBufferSize += ((_constantPoolTypes.getNativeLibraryCount() * 200) + _constantPoolTypes.getNativeLibraryCMDlineStrSizeTotal());
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please remove the outermost parentheses and split this long line:

		requiredBufferSize += (_constantPoolTypes.getNativeLibraryCount() * 200)
				+ _constantPoolTypes.getNativeLibraryCMDlineStrSizeTotal();

I think 200 should be captured in a named constant to clarify the intent.

NativeLibraryEntry *previousNativeLibraryEntry = constantPoolTypes->_previousNativeLibraryEntry;
NativeLibraryEntry *entry = firstNativeLibraryEntry;
PORT_ACCESS_FROM_JAVAVM(constantPoolTypes->_vm);
while (NULL != entry)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggest using a for loop:

		for (; NULL != entry; entry = entry->next) {
...
		}

@@ -1439,6 +1529,14 @@ class VM_JFRConstantPoolTypes {
goto done;
}

_nativeLibrariesTable = pool_new(sizeof(NativeLibraryEntry), 0, sizeof(U_64), 0, J9_GET_CALLSITE(), OMRMEM_CATEGORY_VM, POOL_FOR_PORT(privatePortLibrary));
if(NULL == _nativeLibrariesTable ) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No space before ).

@AditiS11 AditiS11 changed the title Add JFR NativeLibrary Event. Add JFR NativeLibrary event. Apr 15, 2025
@AditiS11 AditiS11 changed the title Add JFR NativeLibrary event. Add JFR NativeLibrary event Apr 15, 2025
@AditiS11 AditiS11 force-pushed the nativelibJFRChunk branch 2 times, most recently from 9baa3e8 to d135dca Compare April 15, 2025 16:37
Copy link
Contributor

@keithc-ca keithc-ca left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please don't end the commit headline with a period. That line should be no more than 70 characters long.

{
NativeLibraryEntry *entry = (NativeLibraryEntry *)anElement;
VM_JFRChunkWriter *writer = (VM_JFRChunkWriter *)userData;
VM_BufferWriter *_bufferWriter = writer->_bufferWriter;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No leading underscore please for local names:

	VM_BufferWriter *bufferWriter = writer->_bufferWriter;

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The other functions in the file followed a similar pattern. Hence I maintained the same pattern.

void
VM_JFRChunkWriter::writeThreadStatisticsEvent(void *anElement, void *userData)
{
        ThreadStatisticsEntry *entry = (ThreadStatisticsEntry *)anElement;
        VM_BufferWriter *_bufferWriter = (VM_BufferWriter *)userData;

Pls do let me know if I should still make the change.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think those other functions should have locals whose names start with an underscore either; but that need not be corrected with this change. I'm only asking that you don't make it worse.

@@ -396,6 +407,8 @@ class VM_JFRConstantPoolTypes {
ClassloaderEntry *_firstClassloaderEntry;
PackageEntry *_previousPackageEntry;
PackageEntry *_firstPackageEntry;
NativeLibraryEntry *_firstNativeLibraryEntry;
NativeLibraryEntry *_previousNativeLibraryEntry;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Perhaps "previous" should be "last"?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All the other events are following the above naming. Pls do let me know if I should still make the change.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I suppose we should follow the established pattern (which I suggest should be fixed, but later).

return 1;
}
newEntry->ticks = j9time_nano_time();
newEntry->name = strdup(libraryName);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggest allocating the copy of the name above before newEntry is allocated to simplify error handling.

@AditiS11 AditiS11 force-pushed the nativelibJFRChunk branch from d135dca to d8cf6b9 Compare April 16, 2025 08:59
Capture libraryName, base and top addresses for each library
@AditiS11 AditiS11 force-pushed the nativelibJFRChunk branch from d8cf6b9 to 0b5b4bb Compare April 16, 2025 11:58
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants