Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to uniquely identify thread in jvmti

i'm working on JVMTI agent and I want to identify same thread on method enter and exit. I'm able to obtain thread name, but that's not sufficient.

Imagine you have a method like this:

public class Main {
    public static void myMethod() {
        System.out.println("doing something as " + Thread.currentThread().getName());
        Thread.currentThread().setName("SomethingDifferent");
        System.out.println("doing something as same thread " + Thread.currentThread().getName());
    }
}

So entering this method will have one name and exiting this thread have different name.

When using JVMTI like this:

static void JNICALL callback_on_method_entry(jvmtiEnv *jvmti, JNIEnv* env,
    jthread thread, jmethodID method)
{
    ...
    (*jvmti)->GetThreadInfo(jvmti, thread, &info);
    ...
}

static void JNICALL callback_on_method_exit(jvmtiEnv *jvmti, JNIEnv *env, jthread thread, jmethodID method, jboolean was_popped_by_exception, jvalue return_value)
{
    ...
    (*jvmti)->GetThreadInfo(jvmti, thread, &info);
    ...
}

Each info will report different thread name and I want to have the same identifier for them.

How can I get the same identifier for the thread ?

One solution can be to get field value of referenced Thread (tid). How to do that ? I can iterat through the heap but I cannot get the field name.

like image 393
czs Avatar asked Oct 30 '22 18:10

czs


2 Answers

One solution, as you pointed out, would be to use GetFieldName. That requires you to lookup the jfieldid, which can be really annoying.

The way i've seen others do it, is to simply assign their own ID's and stash it in the thread local storage. See JavaThreadLayer.cpp from UofO's TAU project, specifically the JavaThreadLayer::GetThreadId() function.

like image 51
lscoughlin Avatar answered Nov 02 '22 10:11

lscoughlin


I finally found another simple soulution:

Because the entry/exit callbacks are running in the same thread, it's possible to use pthread_self() and cast it e.g. to unsigned int. It's not the same tid as you can find in java, but you will get the unique number for thread although the name changes.

like image 28
czs Avatar answered Nov 02 '22 11:11

czs