JVM源码解析Java Attach处理流程

那么JVM自带的这些工具是如何获取到JVM的相关信息呢?JVM提供了 Java Attach 功能,能够让客户端与目标JVM进行通讯从而获取JVM运行时的数据,甚至可以通过Java Attach 加载自定义的代理工具,实现AOP、运行时class热更新等功能。如果我们通过jstack打印线程栈的时候会发现有这么2个线程:Signal Dispatcher和Attach Listener。
摘要由CSDN通过智能技术生成

前言

当Java程序运行时出现CPU负载高、内存占用大等异常情况时,通常需要使用JDK自带的工具jstack、jmap查看JVM的运行时数据,并进行分析。

什么是Java Attach

那么JVM自带的这些工具是如何获取到JVM的相关信息呢?
JVM提供了 Java Attach 功能,能够让客户端与目标JVM进行通讯从而获取JVM运行时的数据,甚至可以通过Java Attach 加载自定义的代理工具,实现AOP、运行时class热更新等功能。

如果我们通过jstack打印线程栈的时候会发现有这么2个线程:Signal Dispatcher和Attach Listener。

"Signal Dispatcher" #4 daemon prio=9 os_prio=2 cpu=0.00ms elapsed=917.19s tid=0x00000164ff377000 nid=0x4ba0 runnable  [0x0000000000000000]
   java.lang.Thread.State: RUNNABLE

"Attach Listener" #5 daemon prio=5 os_prio=2 cpu=0.00ms elapsed=917.19s tid=0x000001648f4d1800 nid=0x1fc0 waiting on condition  [0x0000000000000000]
   java.lang.Thread.State: RUNNABLE

Signal Dispatcher用于处理操作系统信号(软中断信号),Attach Listener线程用于JVM进程间的通信。

操作系统支持的信号可以通过kill -l查看。比如我们平时杀进程用kill -9 可以看到9对应的信号就是SIGKILL。
其他的信号并不会杀掉JVM进程,而是通知到进程, 具体进程如何处理根据Signal Dispatcher线程处理逻辑决定。

root@DESKTOP-45K54QO:~# kill -l
 1) SIGHUP       2) SIGINT       3) SIGQUIT      4) SIGILL       5) SIGTRAP
 6) SIGABRT      7) SIGBUS       8) SIGFPE       9) SIGKILL     10) SIGUSR1
11) SIGSEGV     12) SIGUSR2     13) SIGPIPE     14) SIGALRM     15) SIGTERM
16) SIGSTKFLT   17) SIGCHLD     18) SIGCONT     19) SIGSTOP     20) SIGTSTP
21) SIGTTIN     22) SIGTTOU     23) SIGURG      24) SIGXCPU     25) SIGXFSZ
26) SIGVTALRM   27) SIGPROF     28) SIGWINCH    29) SIGIO       30) SIGPWR
31) SIGSYS      34) SIGRTMIN    35) SIGRTMIN+1  36) SIGRTMIN+2  37) SIGRTMIN+3
38) SIGRTMIN+4  39) SIGRTMIN+5  40) SIGRTMIN+6  41) SIGRTMIN+7  42) SIGRTMIN+8
43) SIGRTMIN+9  44) SIGRTMIN+10 45) SIGRTMIN+11 46) SIGRTMIN+12 47) SIGRTMIN+13
48) SIGRTMIN+14 49) SIGRTMIN+15 50) SIGRTMAX-14 51) SIGRTMAX-13 52) SIGRTMAX-12
53) SIGRTMAX-11 54) SIGRTMAX-10 55) SIGRTMAX-9  56) SIGRTMAX-8  57) SIGRTMAX-7
58) SIGRTMAX-6  59) SIGRTMAX-5  60) SIGRTMAX-4  61) SIGRTMAX-3  62) SIGRTMAX-2
63) SIGRTMAX-1  64) SIGRTMAX

线程初始化

在虚拟机初始完成后,Signal Dispatcher和Attach Listener线程会根据配置进行必要的初始化。

jint Threads::create_vm(JavaVMInitArgs* args, bool* canTryAgain) {
...
  //记录虚拟机初始化完成时间
  Management::record_vm_init_completed();
...
  // 初始化Signal Dispatcher
  os::signal_init();

  // 当设置了StartAttachListener或者无法懒加载时启动Attach Listener
  if (!DisableAttachMechanism) {
    AttachListener::vm_start();
    if (StartAttachListener || AttachListener::init_at_startup()) {
      AttachListener::init();
    }
  }
  ... 
  // 通知所有的 JVMTI agents 虚拟机初始化完成
  JvmtiExport::post_vm_initialized();
  ...
}

相关JVM参数

JVM相关参数如下,默认都是false

JVM参数

默认值

DisableAttachMechanism

false

StartAttachListener

false

ReduceSignalUsage

false

除了这三个参数以外,我们可以看到
AttachListener::init_at_startup()也是用于控制Attach Listener是否初始化。
JDK设计的时候根据不同的操作系

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值