热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

ART虚拟机之Trace原理(转)

一、概述Android6.0系统采用的art虚拟机,所有的Java进程都运行在art之上,当应用发生ANR(ApplicationNotResponse,其中最终的一个环节便是向目标进程发送

一、概述

Android 6.0系统采用的art虚拟机,所有的Java进程都运行在art之上,当应用发生ANR(Application Not Response,其中最终的一个环节便是向目标进程发送信号SIGNAL_QUIT, 传统的linux则是终止程序并输出core;而对于Android进程来说当收到SIGQUIT时,Java层面的进程都是跑在虚拟机之上的,ART虚拟机会捕获该信号,并输出相应的traces信息保存到目录/data/anr/traces.txt。

当然也可以通过一条命令来获取指定进程的traces信息,例如输出pid=888的进程信息:

adb shell kill -3 888 //可指定进程pid 

执行完该命令后traces信息的结果保存到文件/data/anr/traces.txt,如下:

//[见小节2.2] ----- pid 888 at 2016-11-11 22:22:22 ----- Cmd line: system_server ABI: arm Build type: optimized //[见小节3.1] Zygote loaded classes=4113 post zygote classes=3239 //[见小节3.2] Intern table: 57550 strong; 9315 weak //共加载16动态库 [见小节3.3] JNI: CheckJNI is off; globals=2418 (plus 115 weak) Libraries: /system/lib/libandroid.so /system/lib/libandroid_servers.so /system/lib/libaudioeffect_jni.so /system/lib/libcompiler_rt.so /system/lib/libjavacrypto.so /system/lib/libjnigraphics.so /system/lib/libmedia_jni.so /system/lib/librs_jni.so /system/lib/libsechook.so /system/lib/libshell_jni.so /system/lib/libsoundpool.so /system/lib/libwebviewchromium_loader.so /system/lib/libwifi-service.so /vendor/lib/libalarmservice_jni.so /vendor/lib/liblocationservice.so libjavacore.so (16) //已分配堆内存大小40MB,其中29M已用,总分配207772个对象 [见小节3.4] Heap: 27% free, 29MB/40MB; 307772 objects ... //省略GC相关信息 //当前进程总99个线程[见小节3.5] DALVIK THREADS (99): //主线程调用栈[见小节3.6] "main" prio=5 tid=1 Native | group="main" sCount=1 dsCount=0 obj=0x75bd9fb0 self=0x5573d4f770 | sysTid=12078 nice=-2 cgrp=default sched=0/0 handle=0x7fa75fafe8 | state=S schedstat=( 5907843636 827600677 5112 ) utm=453 stm=137 core=0 HZ=100 | stack=0x7fd64ef000-0x7fd64f1000 stackSize=8MB | held mutexes= //内核栈[见小节3.6.2] kernel: __switch_to+0x70/0x7c kernel: SyS_epoll_wait+0x2a0/0x324 kernel: SyS_epoll_pwait+0xa4/0x120 kernel: cpu_switch_to+0x48/0x4c native: #00 pc 0000000000069be4 /system/lib64/libc.so (__epoll_pwait+8) native: #01 pc 000000000001cca4 /system/lib64/libc.so (epoll_pwait+32) native: #02 pc 000000000001ad74 /system/lib64/libutils.so (_ZN7android6Looper9pollInnerEi+144) native: #03 pc 000000000001b154 /system/lib64/libutils.so (_ZN7android6Looper8pollOnceEiPiS1_PPv+80) native: #04 pc 00000000000d4bc0 /system/lib64/libandroid_runtime.so (_ZN7android18NativeMessageQueue8pollOnceEP7_JNIEnvP8_jobjecti+48) native: #05 pc 000000000000082c /data/dalvik-cache/arm64/system@framework@boot.oat (Java_android_os_MessageQueue_nativePollOnce__JI+144) at android.os.MessageQueue.nativePollOnce(Native method) at android.os.MessageQueue.next(MessageQueue.java:323) at android.os.Looper.loop(Looper.java:135) at com.android.server.SystemServer.run(SystemServer.java:290) at com.android.server.SystemServer.main(SystemServer.java:175) at java.lang.reflect.Method.invoke!(Native method) at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:738) at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:628) "Binder_1" prio=5 tid=8 Native | group="main" sCount=1 dsCount=0 obj=0x12c610a0 self=0x5573e5c750 | sysTid=12092 nice=0 cgrp=default sched=0/0 handle=0x7fa2743450 | state=S schedstat=( 796240075 863170759 3586 ) utm=50 stm=29 core=1 HZ=100 | stack=0x7fa2647000-0x7fa2649000 stackSize=1013KB | held mutexes= kernel: __switch_to+0x70/0x7c kernel: binder_thread_read+0xd78/0xeb0 kernel: binder_ioctl_write_read+0x178/0x24c kernel: binder_ioctl+0x2b0/0x5e0 kernel: do_vfs_ioctl+0x4a4/0x578 kernel: SyS_ioctl+0x5c/0x88 kernel: cpu_switch_to+0x48/0x4c native: #00 pc 0000000000069cd0 /system/lib64/libc.so (__ioctl+4) native: #01 pc 0000000000073cf4 /system/lib64/libc.so (ioctl+100) native: #02 pc 000000000002d6e8 /system/lib64/libbinder.so (_ZN7android14IPCThreadState14talkWithDriverEb+164) native: #03 pc 000000000002df3c /system/lib64/libbinder.so (_ZN7android14IPCThreadState20getAndExecuteCommandEv+24) native: #04 pc 000000000002e114 /system/lib64/libbinder.so (_ZN7android14IPCThreadState14joinThreadPoolEb+124) native: #05 pc 0000000000036c38 /system/lib64/libbinder.so (???) native: #06 pc 000000000001579c /system/lib64/libutils.so (_ZN7android6Thread11_threadLoopEPv+208) native: #07 pc 0000000000090598 /system/lib64/libandroid_runtime.so (_ZN7android14AndroidRuntime15javaThreadShellEPv+96) native: #08 pc 0000000000014fec /system/lib64/libutils.so (???) native: #09 pc 0000000000067754 /system/lib64/libc.so (_ZL15__pthread_startPv+52) native: #10 pc 000000000001c644 /system/lib64/libc.so (__start_thread+16) (no managed stack frames) ... //此处省略剩余的N个线程. 

 

实例:

"Binder_1" prio=5 tid=8 Native | group="main" sCount=1 dsCount=0 obj=0x12c610a0 self=0x5573e5c750 | sysTid=12092 nice=0 cgrp=default sched=0/0 handle=0x7fa2743450 | state=S schedstat=( 796240075 863170759 3586 ) utm=50 stm=29 core=1 HZ=100 | stack=0x7fa2647000-0x7fa2649000 stackSize=1013KB | held mutexes= 

解释:

  1. 第一行:线程名(“Binder_1”)(如果带有daemon说明是守护线程,线程优先级(“prio=5”),线程内部id(“tid=8”),线程状态(“NATIVE”)。
  2. 第二行: 线程所属的线程组 (“main”),线程挂起次数(“sCount=1”),用于调试的线程挂起次数(”dsCount=0“), 当前线程关联的java线程对象(”obj=0x12c610a0“),该线程地址(“self=0x5573e5c750”)。
  3. 第三行:线程真正意义上的tid(“sysTid=12092”),调度有优先级(“nice=0”), 优先组属(“cgrp=default”),调度策略(sched=0/0), 处理函数地址(“handle=0x7fa2743450”)
  4. 第四行: 线程状态(S), 调度时间统计schedstat,线程用户态下使用的时间值(单位是jiffies)(“utm=50”), 内核态下得调度时间值(“stm=20”),最后运行该线程的核(“core=1”)
  5. 第五行:线程栈的地址区间(“0x7fa2647000-0x7fa2649000”),以及栈的大小(“1013KB”)
  6. 第六行:所持有的mutex类型,有独占锁exclusive和共享锁shared两类。

说明:

  • CPU调度统计信息(schedstat):通过读取节点/proc/[pid]/task/[tid]/schedstat
  • CPU使用统计:通过读取节点/proc/self/task/[tid]/stat
  • 内核栈:通过读取节点/proc/self/task/[tid]/stack
  • jiffies系统的节拍数,该值是1/HZ,一般来说100HZ,也就意味着1jiffies = 10ms.
  • 线程状态:除了Native,另外还有Running, Blocked等状态,进程没有依附的状态(not attached)

 

转自:http://gityuan.com/2016/11/26/art-trace/


推荐阅读
  • Ubuntu18.04 安装ROS Melodic && Ros2 Dashing
    https:blog.csdn.netqq_44717317articledetails104547474一、Ubuntu18.04的安装ubuntu2go的制作关于Ubuntu2 ... [详细]
  • Android系统源码分析Zygote和SystemServer启动过程详解
    本文详细解析了Android系统源码中Zygote和SystemServer的启动过程。首先介绍了系统framework层启动的内容,帮助理解四大组件的启动和管理过程。接着介绍了AMS、PMS等系统服务的作用和调用方式。然后详细分析了Zygote的启动过程,解释了Zygote在Android启动过程中的决定作用。最后通过时序图展示了整个过程。 ... [详细]
  • Linux服务器密码过期策略、登录次数限制、私钥登录等配置方法
    本文介绍了在Linux服务器上进行密码过期策略、登录次数限制、私钥登录等配置的方法。通过修改配置文件中的参数,可以设置密码的有效期、最小间隔时间、最小长度,并在密码过期前进行提示。同时还介绍了如何进行公钥登录和修改默认账户用户名的操作。详细步骤和注意事项可参考本文内容。 ... [详细]
  • 本文介绍了在Win10上安装WinPythonHadoop的详细步骤,包括安装Python环境、安装JDK8、安装pyspark、安装Hadoop和Spark、设置环境变量、下载winutils.exe等。同时提醒注意Hadoop版本与pyspark版本的一致性,并建议重启电脑以确保安装成功。 ... [详细]
  • 本文介绍了Hyperledger Fabric外部链码构建与运行的相关知识,包括在Hyperledger Fabric 2.0版本之前链码构建和运行的困难性,外部构建模式的实现原理以及外部构建和运行API的使用方法。通过本文的介绍,读者可以了解到如何利用外部构建和运行的方式来实现链码的构建和运行,并且不再受限于特定的语言和部署环境。 ... [详细]
  • Linux如何安装Mongodb的详细步骤和注意事项
    本文介绍了Linux如何安装Mongodb的详细步骤和注意事项,同时介绍了Mongodb的特点和优势。Mongodb是一个开源的数据库,适用于各种规模的企业和各类应用程序。它具有灵活的数据模式和高性能的数据读写操作,能够提高企业的敏捷性和可扩展性。文章还提供了Mongodb的下载安装包地址。 ... [详细]
  • Go Cobra命令行工具入门教程
    本文介绍了Go语言实现的命令行工具Cobra的基本概念、安装方法和入门实践。Cobra被广泛应用于各种项目中,如Kubernetes、Hugo和Github CLI等。通过使用Cobra,我们可以快速创建命令行工具,适用于写测试脚本和各种服务的Admin CLI。文章还通过一个简单的demo演示了Cobra的使用方法。 ... [详细]
  • 本文介绍了如何使用C#制作Java+Mysql+Tomcat环境安装程序,实现一键式安装。通过将JDK、Mysql、Tomcat三者制作成一个安装包,解决了客户在安装软件时的复杂配置和繁琐问题,便于管理软件版本和系统集成。具体步骤包括配置JDK环境变量和安装Mysql服务,其中使用了MySQL Server 5.5社区版和my.ini文件。安装方法为通过命令行将目录转到mysql的bin目录下,执行mysqld --install MySQL5命令。 ... [详细]
  • 本文介绍了Windows操作系统的版本及其特点,包括Windows 7系统的6个版本:Starter、Home Basic、Home Premium、Professional、Enterprise、Ultimate。Windows操作系统是微软公司研发的一套操作系统,具有人机操作性优异、支持的应用软件较多、对硬件支持良好等优点。Windows 7 Starter是功能最少的版本,缺乏Aero特效功能,没有64位支持,最初设计不能同时运行三个以上应用程序。 ... [详细]
  • Imtryingtofigureoutawaytogeneratetorrentfilesfromabucket,usingtheAWSSDKforGo.我正 ... [详细]
  • centos安装Mysql的方法及步骤详解
    本文介绍了centos安装Mysql的两种方式:rpm方式和绿色方式安装,详细介绍了安装所需的软件包以及安装过程中的注意事项,包括检查是否安装成功的方法。通过本文,读者可以了解到在centos系统上如何正确安装Mysql。 ... [详细]
  • 解决Sharepoint 2013运行状况分析出现的“一个或多个服务器未响应”问题的方法
    本文介绍了解决Sharepoint 2013运行状况分析中出现的“一个或多个服务器未响应”问题的方法。对于有高要求的客户来说,系统检测问题的存在是不可接受的。文章详细描述了解决该问题的步骤,包括删除服务器、处理分布式缓存留下的记录以及使用代码等方法。同时还提供了相关关键词和错误提示信息,以帮助读者更好地理解和解决该问题。 ... [详细]
  • Python脚本编写创建输出数据库并添加模型和场数据的方法
    本文介绍了使用Python脚本编写创建输出数据库并添加模型数据和场数据的方法。首先导入相应模块,然后创建输出数据库并添加材料属性、截面、部件实例、分析步和帧、节点和单元等对象。接着向输出数据库中添加场数据和历程数据,本例中只添加了节点位移。最后保存数据库文件并关闭文件。文章还提供了部分代码和Abaqus操作步骤。另外,作者还建立了关于Abaqus的学习交流群,欢迎加入并提问。 ... [详细]
  • Tomcat安装与配置教程及常见问题解决方法
    本文介绍了Tomcat的安装与配置教程,包括jdk版本的选择、域名解析、war文件的部署和访问、常见问题的解决方法等。其中涉及到的问题包括403问题、数据库连接问题、1130错误、2003错误、Java Runtime版本不兼容问题以及502错误等。最后还提到了项目的前后端连接代码的配置。通过本文的指导,读者可以顺利完成Tomcat的安装与配置,并解决常见的问题。 ... [详细]
  • 生产环境下JVM调优参数的设置实例
     正文前先来一波福利推荐: 福利一:百万年薪架构师视频,该视频可以学到很多东西,是本人花钱买的VIP课程,学习消化了一年,为了支持一下女朋友公众号也方便大家学习,共享给大家。福利二 ... [详细]
author-avatar
sl51866
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有