• bootchart 使用说明及代码分析


    简介:

    bootchart是一个用于linux启动过程性能分析的开源软件工具,在系统启动过程自动收集CPU占用率、进程等信息,并以图形方式显示分析结果,可用作指导优化系统启动过程。

    bootchart是一个对linux启动流程进行分析得开源软件工具。android中有集成bootchart源码,路径为system/core/init/bootchart.c

     
    第一部分:先从具体使用流程如下


    1、编译android中的bootchart(缺省时不被编译)
      在android源码system/core/init/目录执行: mm INIT_BOOTCHART=true -B

      或者直接修改 Android.mak文件

    1. <span style="font-size:14px;color:#333333;">    LOCAL_PATH:= $(call my-dir)  
    2.     include $(CLEAR_VARS)  
    3.       
    4.     INIT_BOOTCHART := true  </span>  

    2、将新编译的android系统镜像烧录到android设备中。
    编译生成新的可执行文件init,该文件在手机文件系统位于根/下,对应的flash image是boot.img,为此需重新烧写含有新的init的boot.img


    3、在手机上创建文件/data/bootchart-start,其内容是bootchart的采样时间
    adb shell 'echo $TIMEOUT > /data/bootchart-start'
    其中$TIMEOUT是期望采样的时间,单位为秒,例如要采样两分钟,则执行:
    adb shell 'echo 120 > /data/bootchart-start'


    4、重启设备,init运行时将自动创建文件夹/data/bootchart/,并在其中保存采样数据,采样数据由5个文件组成:

    1. <span style="font-size:14px;color:#333333;">-rw-rw-rw- root     root          732 1970-01-01 08:00 header  
    2. -rw-r--r-- root     root            0 1970-01-01 08:00 kernel_pacct  
    3. -rwxr-xr-x root     root       517150 2014-04-09 12:06 proc_diskstats.log  
    4. -rwxr-xr-x root     root      2783967 2014-04-09 12:06 proc_ps.log  
    5. -rwxr-xr-x root     root       152090 2014-04-09 12:06 proc_stat.log</span>  


    需要注意,在手机上运行bootchart采样完成后若不再使用bootchart则需手工删除文件/data/bootchart-start,否则手机每次重启时都会运行bootchart。


    5、文件打包
    在/data/bootchart/目录下执行命令:

    1. <span style="font-size:14px;color:#333333;">busybox tar -czf bootchart.tgz header proc_stat.log proc_ps.log proc_diskstats.log kernel_pacct </span>  

    然后将生成bootchart.tgz用u盘拷贝到电脑(ubuntu系统)上。

    也可手工通过adb pull将这5个文件上传到PC并打包,反正最终就是生成 bootchart.tgz 


    6.在电脑上安装bootchart工具

    使用sudo apt-get install bootchart 命令安装, 如果出现 bootchart无法正常解析android中生成的bootchart.tgz文件。
    需要使用老版本的安装包bootchart_0.9-0ubuntu6_all.deb,可以在此下载http://download.csdn.net/detail/sckgenius/7166477。
    先sudo apt-get install librsvg2-bin,然后sudo dpkg -i bootchart_0.9-0ubuntu6_all.deb 。


    7、执行下面的命令生成分析结果图表,缺省生成png格式的图像文件bootchart.png:
    java -jar /usr/share/bootchart/bootchart.jar /path/to/bootchart.tgz

    这里上传一张bootchart.png图:



    第二部分:下面说一下bootchart是如何得到这些数据信息的


    分析是源码:systemcoreinitootchart.c 只有一个文件


    1、启动

    init.c 中通过宏定义 BOOTCHART 增加代码

    1. <span style="font-size:14px;color:#333333;">#if BOOTCHART  
    2. static int bootchart_init_action(int nargs, char **args)  
    3. {  
    4.     bootchart_count = bootchart_init();  
    5.     if (bootchart_count < 0) {  
    6.         ERROR("bootcharting init failure ");  
    7.     } else if (bootchart_count > 0) {  
    8.         NOTICE("bootcharting started (period=%d ms) ", bootchart_count*BOOTCHART_POLLING_MS);  
    9.     } else {  
    10.         NOTICE("bootcharting ignored ");  
    11.     }  
    12.   
    13.     return 0;  
    14. }  
    15. #endif</span>  


    通过调用 bootchart_init() 启动


    2、周期性执行

    int main(int argc, char **argv)

    1. <span style="font-size:14px;"><span style="color:#333333;">{  
    2.   
    3. #if BOOTCHART  
    4.     queue_builtin_action(bootchart_init_action, "bootchart_init");  
    5. #endif  
    6.   
    7.     for(;;) {  
    8.         int nr, i, timeout = -1;  
    9.   
    10.   
    11. #if BOOTCHART  
    12.         if (bootchart_count > 0) {  
    13.             if (timeout < 0 || timeout > BOOTCHART_POLLING_MS)  
    14.                 timeout = BOOTCHART_POLLING_MS;  
    15.             if (</span><strong><span style="color:#FF0000;">bootchart_step(</span><span style="color:#CC0000;">)</span></strong><span style="color:#333333;"> < 0 || --bootchart_count == 0) {  
    16.                 bootchart_finish();  
    17.                 bootchart_count = 0;  
    18.             }  
    19.         }  
    20. #endif  
    21.   
    22.         nr = poll(ufds, fd_count, timeout);  
    23.           
    24.   }   
    25.     ...  
    26. }</span></span>  

    默认周期时间:
    # define BOOTCHART_POLLING_MS   200   /* polling period in ms */


    3、具体如何采样数据

    分析一下源码就很清楚了,就是通过linux中的标准命令(shell上执行cat xxx 类似)并将其结果写入相应的文件

    /proc/cmdline
    /proc/version
    /proc/cpuinfo
    写入到文件 #define LOG_HEADER      LOG_ROOT"/header"

    /proc/uptime
    /proc/stat
    写入到文件 #define LOG_STAT        LOG_ROOT"/proc_stat.log"

    /proc/uptime
    /proc/diskstats
    写入到文件 #define LOG_DISK        LOG_ROOT"/proc_diskstats.log"

    /proc/uptime
    /proc/$PID/cmdline
    /proc/$PID/stat
    写入到文件 #define LOG_PROCS       LOG_ROOT"/proc_ps.log"

    这个文件只打开,没有写入什么内容
    /* create kernel process accounting file */
    #define LOG_ACCT        LOG_ROOT"/kernel_pacct"


    参考资料:

    1、system/core/init/README.BOOTCHART

    2、http://www.bootchart.org/index.html

  • 相关阅读:
    操作系统第一章绪论
    JavaScript推断E-mail地址是否合法
    projecteuler----&gt;problem=8----Largest product in a series
    QQ聊天原理初识
    窗体和线程漫谈之工作线程怎样将数据的处理结果显示到窗体
    Swift
    iOS-UIApplication详解
    iOS开发拓展篇——如何把项目托管到GitHub
    Swift
    Swift
  • 原文地址:https://www.cnblogs.com/jasonleeee/p/4561533.html
Copyright © 2020-2023  润新知