首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >JVMTI RetransformClasses()需要很长时间

JVMTI RetransformClasses()需要很长时间
EN

Stack Overflow用户
提问于 2016-12-26 07:22:20
回答 1查看 826关注 0票数 3

我部署了一个简单的JVMTI代理来测试字节码检测。我的策略是在RetransformClasses中调用CompiledMethodLoad函数,回调来调用ClassFileLoadHook。为此,我编写了以下代码:

代码语言:javascript
复制
    err = (*jvmti)->GetMethodDeclaringClass(jvmti, method, &klass);
    check_jvmti_error(jvmti, err, "Get Declaring Class");

    err = (*jvmti)->RetransformClasses(jvmti, 1, &klass);
    check_jvmti_error(jvmti, err, "Retransform class");

这个函数通过调用ClassFileLoadHook事件正确地工作,但是当我只是在其中传递同一个类时,它会花费大量的时间。我的ClassFileLoadHook回调函数是空的。我在计算一个简单的矩阵乘法算法的时间。通过注释掉RetransformClasses函数,得到0.8 seconds顺序的执行时间。而仅仅编写这个函数就会将执行时间提高到15 seconds周围。

它应该承担那么多的开销,还是我做错了什么?

问候

代码:

代码语言:javascript
复制
static int x = 1;
void JNICALL
compiled_method_load(jvmtiEnv *jvmti, jmethodID method, jint code_size,
        const void* code_addr, jint map_length, const jvmtiAddrLocationMap* map,
        const void* compile_info) {
    jvmtiError err;
    jclass klass;

    char* name = NULL;
    char* signature = NULL;
    char* generic_ptr = NULL;

    err = (*jvmti)->RawMonitorEnter(jvmti, lock);
    check_jvmti_error(jvmti, err, "raw monitor enter");

    err = (*jvmti)->GetMethodName(jvmti, method, &name, &signature,
            &generic_ptr);
    check_jvmti_error(jvmti, err, "Get Method Name");

    printf("\nCompiled method load event\n");
    printf("Method name %s %s %s\n\n", name, signature,
            generic_ptr == NULL ? "" : generic_ptr);

    if (strstr(name, "main") != NULL && x == 1) {
        x++;
        err = (*jvmti)->GetMethodDeclaringClass(jvmti, method, &klass);
        check_jvmti_error(jvmti, err, "Get Declaring Class");

        err = (*jvmti)->RetransformClasses(jvmti, 1, &klass);
        check_jvmti_error(jvmti, err, "Retransform class");

    }

    if (name != NULL) {
        err = (*jvmti)->Deallocate(jvmti, (unsigned char*) name);
        check_jvmti_error(jvmti, err, "deallocate name");
    }
    if (signature != NULL) {
        err = (*jvmti)->Deallocate(jvmti, (unsigned char*) signature);
        check_jvmti_error(jvmti, err, "deallocate signature");
    }
    if (generic_ptr != NULL) {
        err = (*jvmti)->Deallocate(jvmti, (unsigned char*) generic_ptr);
        check_jvmti_error(jvmti, err, "deallocate generic_ptr");
    }

    err = (*jvmti)->RawMonitorExit(jvmti, lock);
    check_jvmti_error(jvmti, err, "raw monitor exit");
}
EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2017-02-03 07:28:09

回答我的问题:

不是的。我没做错什么。应该花那么多时间在头顶上。

--这是证据:

我用吉特沃特来了解这个问题。我分析了JIT调用后的ClassLoad时间检测和检测。在这两种情况下,我都使用相同的应用程序代码。

类加载时间仪表

执行时间:18秒左右。

JIT调用过程中的工具

执行时间:80秒左右。

结论

我们可以在这里清楚地看到,当我试图通过调用RetransformClasses -> CLassFileLoadHook序列在CompiledLoadEvent中对代码进行测试时,JIT简单地停止,然后就不会为我试图检测的函数被调用。之后,它甚至不进行OSR编译。我在这个回答中总结了JIT行为的原因。后续问题给出了这里。任何知道解决办法的人都是最欢迎回答的。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/41327794

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档