关闭

jstat java工具在linux上的源码分析

标签: 工具javalinuxresourcesuserbuffer
3639人阅读 评论(3) 收藏 举报
分类:

jstat通常是作为使用查看gc 状态,编译信息等具体信息,加载class量等,笔者在前面的博客里谈了jmap,jstack工具的如何实现可具体参考(http://blog.csdn.net/raintungli/article/details/7023092) ,谈到通常的方法必须让jvm的所有线程进入一个safe point的状态,也就是在使用jmap, jstack工具的时候会有线程的停顿感,并且影响到当时jvm所正在处理的事情,如果在产线上这是会影响客户体验的。

 在调用jstat 的时候,并没有感觉到线程的停顿,也就是jstat 使用与jmap,jstack完全不同的方式,接着还是源码分析来解释。

在jstat.java中初始化LocalMonitoredVM中,初始化了PerfDataBuffer, 在PerfDataBuffer是通过Perf attach vm的进程生成byte buffer对象

  private ByteBuffer attachImpl(String user, int lvmid, int mode)
            throws IllegalArgumentException, IOException
    {
        final ByteBuffer b = attach(user, lvmid, mode);

        if (lvmid == 0) {
            // The native instrumentation buffer for this Java virtual
            // machine is never unmapped.
            return b;
        }
        else {
            // This is an instrumentation buffer for another Java virtual
            // machine with native resources that need to be managed. We
            // create a duplicate of the native ByteBuffer and manage it
            // with a Cleaner object (PhantomReference). When the duplicate
            // becomes only phantomly reachable, the native resources will
            // be released.

            final ByteBuffer dup = b.duplicate();
            Cleaner.create(dup, new Runnable() {
                    public void run() {
                        try {
                            instance.detach(b);
                        }
                        catch (Throwable th) {
                            // avoid crashing the reference handler thread,
                            // but provide for some diagnosability
                            assert false : th.toString();
                        }
                    }
                });
            return dup;
        }
    }
    private native ByteBuffer attach(String user, int lvmid, int mode)
                   throws IllegalArgumentException, IOException;

关键就在native程序中, 查看perf.cpp 中对应的方法

PerfMemory::attach(user_utf, vmid, (PerfMemory::PerfMemoryMode) mode,
                     &address, &capacity, CHECK_NULL);

也就是类PerfMemory的attach方法

在perfMemory_linux.cpp中,我们看到了attach 的实现

void PerfMemory::attach(const char* user, int vmid, PerfMemoryMode mode, char** addrp, size_t* sizep, TRAPS) {

  if (vmid == 0 || vmid == os::current_process_id()) {
     *addrp = start();
     *sizep = capacity();
     return;
  }

  mmap_attach_shared(user, vmid, mode, addrp, sizep, CHECK);
}

在mmap_attach_shared函数中,

 char* filename = get_sharedmem_filename(dirname, vmid);

  // copy heap memory to resource memory. the open_sharedmem_file
  // method below need to use the filename, but could throw an
  // exception. using a resource array prevents the leak that
  // would otherwise occur.
  char* rfilename = NEW_RESOURCE_ARRAY(char, strlen(filename) + 1);
  strcpy(rfilename, filename);

  // free the c heap resources that are no longer needed
  if (luser != user) FREE_C_HEAP_ARRAY(char, luser);
  FREE_C_HEAP_ARRAY(char, dirname);
  FREE_C_HEAP_ARRAY(char, filename);

  // open the shared memory file for the give vmid
  fd = open_sharedmem_file(rfilename, file_flags, CHECK);
  assert(fd != OS_ERR, "unexpected value");

  if (*sizep == 0) {
    size = sharedmem_filesize(fd, CHECK);
    assert(size != 0, "unexpected size");
  }

  mapAddress = (char*)::mmap((char*)0, size, mmap_prot, MAP_SHARED, fd, 0);

该函数把一个文件mmap成内存,然后通过读取内存来读取该文件的内容,而文件的路径就是/tmp/hsperfdata_{userid}/{pid} 

而在create_shared_memory函数中,也就是jvm 在vm_init_globals初始化后会创建这个文件并且用mmap映射成内存,接着虚拟机会把gc 或者其他需要的状态写入这个mmap文件中,jstat工具通过访问该文件,读取内容,显示在屏幕上,该文件通过内存映射实现,没有什么性能损耗,完整的jstat 的流程就全部走通了。





1
0
查看评论
发表评论
* 以上用户言论只代表其个人观点,不代表CSDN网站的观点或立场

JVM源码分析之Jstat工具原理完全解读

摘要: 概述 jstat是hotspot自带的工具,和java一样也位于JAVA_HOME/bin下面,我们通过该工具可以实时了解当前进程的gc,compiler,class,memory等相关的情况...
  • shuyun123456789
  • shuyun123456789
  • 2016-12-13 11:19
  • 715

jstat使用详解(分析JVM的使用情况)

jstat 命令格式如下所示为jstat的命令格式jstat - [-t] [-h] [ []]如下表示分析进程id为31736 的gc情况,每隔1000ms打印一次记录,打印10次停止,每3行后打...
  • ouyang111222
  • ouyang111222
  • 2016-12-18 16:53
  • 1859

JVM调优总结 + jstat 分析

jstat -gccause pid 1 每格1毫秒输出结果 jstat -gccause pid 2000 每格2秒输出结果 不断的在屏幕打印出结果   S0   ...
  • xingxiupaioxue
  • xingxiupaioxue
  • 2016-10-14 17:14
  • 1929

JVM调优总结 + jstat 分析

原文地址:http://blog.163.com/bobile45@126/blog/static/9606199220139303343415/ jstat -gccause pid ...
  • wayne_2015
  • wayne_2015
  • 2017-05-04 14:04
  • 973

Jstat使用详解

1.jps可以理解成java进程的ps,也就是罗列出所有的正在运行的Java进程; 2.jstat 一个极强的一个VM监控工具;jstat -gcutil pid 可以查看对应该id进程的gc所有状...
  • Barnetthe
  • Barnetthe
  • 2015-08-05 15:37
  • 2576

jstat命令详解

Jstat是JDK自带的一个轻量级小工具。全称“Java Virtual Machine statistics monitoring tool”,它位于java的bin目录下,主要利用JVM内建的指令...
  • zhaozheng7758
  • zhaozheng7758
  • 2013-02-28 19:49
  • 45173

jstat分析JVM内存

出处:http://liulinxia02.blog.163.com/blog/static/268687720117251501253/ Jstat 是JDK自带的一个轻量级小工具。全称“Java...
  • preterhuman_peak
  • preterhuman_peak
  • 2015-02-09 19:16
  • 12149

JVM性能调优监控工具jps、jstack、jmap、jhat、jstat、hprof使用详解 - 实例分析

JVM性能调优监控工具jps、jstack、jmap、jhat、jstat、hprof使用详解 - 实例分析 原文  http://josh-persistence.iteye.com/blog/2...
  • u013516966
  • u013516966
  • 2017-07-28 21:33
  • 1392

Linux使用jstat命令查看jvm的GC情况

命令格式 jstat命令命令格式: jstat [Options] vmid [interval] [count] 参数说明: Options,选项,我们一般使用 -gcutil 查看gc...
  • shuyun123456789
  • shuyun123456789
  • 2017-03-10 14:45
  • 888

JVM性能调优监控工具jps、jstack、jmap、jhat、jstat等使用详解

javap 和 javac javap -help javac -help jps jps -help jstack jstack -help jstat 参考文章 jmap jmap -help ...
  • tzs_1041218129
  • tzs_1041218129
  • 2017-03-12 20:19
  • 2354
    个人资料
    • 访问:485687次
    • 积分:5334
    • 等级:
    • 排名:第5942名
    • 原创:99篇
    • 转载:3篇
    • 译文:0篇
    • 评论:73条
    最新评论