前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >JVMTI第二种实现Agent方式

JVMTI第二种实现Agent方式

作者头像
用户1418372
发布2020-02-13 12:59:08
1.1K0
发布2020-02-13 12:59:08
举报
文章被收录于专栏:清晨我上码清晨我上码

Agent第二种实现方式

上一部分第一种和本节基本相同,具体如下:

编写java动态执行代码

代码语言:javascript
复制
package abc;
import java.io.IOException;
import com.sun.tools.attach.VirtualMachine;

public class VMAttacher {

    public static void main(String[] args) throws Exception {
     // args[0]为java进程id
         System.out.println(args[0]);
         VirtualMachine virtualMachine = com.sun.tools.attach.VirtualMachine.attach(args[0]);
         System.out.println(virtualMachine.getClass());
         System.out.println("==========contintue");
         // args[1]为共享库路径
         virtualMachine.loadAgentPath(args[1], null);
         virtualMachine.detach();
    }

}

编译java程序生成class文件,指定额外的依赖

javac -Djava.ext.dirs=C:\jdk1.8.0_101\lib ./abc/VMAttacher.java

编写cpp代码打印加载的类信息

代码语言:javascript
复制
//如果引入失败可以直接指定文件地址例如 "./jvm/jvmti.h"
#include <jvmti.h>
#include <string>
#include <cstring>
#include <iostream>
#include <list>
#include <map>
#include <set>
#include <stdlib.h>
#include <jni_md.h>
using namespace std;
JNIEXPORT jint JNICALL Agent_OnAttach(JavaVM* jvm, char* options,
    void* reserved) {
    jvmtiEnv* jvmti;
    jint result = jvm->GetEnv((void**)&jvmti, JVMTI_VERSION_1_1);
    if (result != JNI_OK) {
        printf("ERROR: Unable to access JVMTI!\n");
    }
    jvmtiError err = (jvmtiError)0;
    jclass* classes;
    jint count;

    err = jvmti->GetLoadedClasses(&count, &classes);
    if (err) {
        printf("ERROR: JVMTI GetLoadedClasses failed!\n");
    }
    for (int i = 0; i < count; i++) {
        char* sig;
        jvmti->GetClassSignature(classes[i], &sig, NULL);
        printf("cls sig=%s\n", sig);
    }
    return err;
}

JNIEXPORT void JNICALL Agent_OnUnload(JavaVM* vm) {
    cout << "Agent_OnUnload(" << vm << ")" << endl;
}

生成动态链接库:

cl /EHsc -I

{JAVA_HOME}/include/ -I
{JAVA_HOME}/include/ -I

{JAVA_HOME}/include/win32 -LD Agent2.cpp -FeAgent2.dll

代码语言:javascript
复制
用于 x64 的 Microsoft (R) C/C++ 优化编译器 19.24.28314 版
版权所有(C) Microsoft Corporation。保留所有权利。

Agent2.cpp
Microsoft (R) Incremental Linker Version 14.24.28314.0
Copyright (C) Microsoft Corporation.  All rights reserved.

/dll
/implib:Agent2.lib
/out:Agent2.dll
Agent2.obj
  正在创建库 Agent2.lib 和对象 Agent2.exp

完成,后动态启动加载该链接库到对应的jvm中

执行

java -Djava.ext.dirs=./lib -cp ./ abc.VMAttacher 12345 /xx/Agent2.dll

  • lib文件下是拷贝jdk lib下的tools.jar

执行成功后,可以在对应的进程12345下看到下面jvmti打印的日志

代码语言:javascript
复制
class signature=Lorg/springframework/core/ReactiveAdapterRegistry$ReactorRegistrar$$Lambda$517/1273048940;
class signature=Lorg/springframework/core/ReactiveAdapterRegistry$ReactorRegistrar$$Lambda$516/375201108;
....
...
  • 以上就是两种实现方式了,具体可以根据需求实现具体的业务逻辑
本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • Agent第二种实现方式
  • 编写java动态执行代码
  • 编写cpp代码打印加载的类信息
  • 生成动态链接库:
  • 执行
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档