Android驅動筆記(8)——bugreport介紹


8.1、概述及應用場景

 安卓bugreport主要用於分析手機的狀態。其包含:main log,kernel log,cpuinfo等信息。bugreport是一個可執行文件,編譯后的路徑為system/bin/bugreport,源碼位於framework/native/cmds/bugreport。其核心在於啟動dumpsys服務。bugreport同dumpstate服務建立socket通信(建立連接20次,超時3min無數據等容錯)。連接之后,將接收到的數據定向到文件中。
  因此我們看到的bugreport數據均來自dumpstate。

  1. print_header(string):讀取了需要顯示的prop如fingerprint,build type等等。
  2. dump_systrace():將systemtrace.txt文件加入到bugreport.zip中。
  3. dump_raft():將raftlog.txt文件加入到bugreport.zip中。

8.2、bugreport流程梳理

  1. 提高dumpsate進程的優先級,防止被OOM Killer殺死
  2. 參數解析(adb shell dumpstate -h)
  3. (打開vibrator,在執行bugreport時,先震動一下提醒)
  4. 通過dump_traces()來完成收集虛擬機和native進程的stack traces
  5. 通過get_tombstone_fds來獲取tombstone文件描述符
  6. 開始執行切換到非root用戶和組,在這之前的執行都處於root權限
  7. 執行dumpstate()主要過程都在這里執行
  8. 再次通過震動以提醒dump操作執行完成
  9. 發送廣播,告知ActivityManager已完成bugreport操作

8.3、小結

 bugreport通過socket與dumpstate服務建立通信,在dumpstate.cpp中的dumpstate()方法完成核心功能。分別輸出:current log、 last log、 vm trace、 dumpsys、 system info
 其詳細內容主要有:系統build及運行時長等信息、 內存和CPU進程的信息、 kernel log、 system log、 radio log、 event log等等。實際來說,bugreport中顯示的大部分為信息,都有對應的命令方式可以獲取。bugreport只是作為一個在不打擾用戶的前提下執行的一套命令集合。

8.4、bugreport的解析方法

 有以下兩種辦法可以更加方便地解析bugreport。

  1. 推薦使用Sony開源的一款checkbugreport的工具來解析成一個html文件。

安裝java環境
在cmd 窗口中執行 java -jar {path}/checkbugreport.jar {path}/bugreport.log
解析好的文件在bugreport log文件夾中會生成 bugreport_out的文件夾,打開index.html即可以查看。

  1. 推薦google的開源工具:https://github.com/google/battery-historian
     這個工具需要FQ,借助google解析,本地搭建環境也不復雜,看情況有時間出教程。

8.5、Dumpsys sensorservices解析

 作為一個sensor工程師,這是一個必備的技能。
Dumpsys sensorservices用於查看當前設備sensor的使用情況。可通過_adb shell dumpsys sensorservice_獲取。開頭提供了Active sensors的信息:

Active sensors:
BMI120 Accelerometer (handle=0x00000001, connections=3)
stk3x3x alsprx (handle=0x00000008, connections=1)
Step Counter (handle=0x00000015, connections=3)
Step Detector -Wakeup Secondary (handle=0x00000021, connections=1)
Socket Buffer size = 984 events
WakeLock Status: not held
Mode : NORMAL

其中有加速度計、光線距離感應器、步進計數器、步進探測器等。

8 active connections
Connection Number: 0
   Operating Mode: NORMAL //對應到前面的Mode
    com.tencent.mm.plugin.sport.model.g | WakeLockRefCount 0 | uid 10161 | cache size 0 | max cache size 0 
    //這里只能顯示uid,並不能顯示pid,通過uid,可以在/data/system/package.list看到對應的package name
    Step Counter 0x00000015 | status: active | pending flush events 0
Connection Number: 1
   Operating Mode: NORMAL
    android.view.OrientationEventListener | WakeLockRefCount 0 | uid 10160 | cache size 0 | max cache size 0
    BMI120 Accelerometer 0x00000001 | status: active | pending flush events 0
Connection Number: 2
   Operating Mode: NORMAL

有些情況下,兩個APP的uid是一樣的,這時就需要pid來進行區分,想要看到app運行的pid信息,需要在sensorservice中增加一些code才可以。打開_frameworks\native\services\sensorservice\SensorService.h_
增加如下內容:

uid_t mUid;
pid_t mPid; //Debug

在_frameworks\native\services\sensorservice\SensorService.cpp_文件中添加:

SensorService::SensorEventConnection::SensorEventConnection(
   mChannel = new BitTube(mService->mSocketBufferSize);
   mPid = IPCThreadState::self()->getCallingPid(); //Debug
   ...)
SensorService::SensorEventConnection::Dump(String8& result){
   result.appendFormat("\t WakeLockRefCount %d pid %d | uid %d | ..., mPid, mUid");
}

增加上面的內容以后就可以在sensorservice中打印出pid信息。

Previous Registrations:
14:50:16 + 0x00000001 pid= 3580 uid=10160 package=android.view.OrientationEventListener samplingPeriod=200000us batchingPeriod=0us
14:50:16 + 0x00000001 pid= 3580 uid=10160 package=android.view.OrientationEventListener samplingPeriod=200000us batchingPeriod=0us
14:50:16 - 0x00000001 pid= 3580 uid=10160 package=android.view.OrientationEventListener
14:50:16 + 0x00000001 pid= 3580 uid=10160 package=android.view.OrientationEventListener samplingPeriod=200000us batchingPeriod=0us
14:48:27 + 0x00000015 pid= 5314 uid=10161 package=com.tencent.mm.plugin.sport.model.g samplingPeriod=600000us batchingPeriod=0us
14:48:21 + 0x00000015 pid= 3390 uid=10161 package=com.tencent.mm.plugin.sport.model.c samplingPeriod=600000us batchingPeriod=0us
14:48:18 + 0x00000021 pid= 4975 uid= 1000 package=com.xiaomi.joyose.stepsprovider.StepsService samplingPeriod=200000us batchingPeriod=300000000us
14:48:18 - 0x00000007 pid= 2480 uid= 1000 package=miui.util.ProximitySensorWrapper
14:48:17 + 0x00000015 pid= 3251 uid=10160 package=com.tencent.mobileqq.msf.core.ad samplingPeriod=200000us batchingPeriod=360000000us
14:48:14 + 0x00000001 pid= 2288 uid= 1000 package=com.android.server.policy.WindowOrientationListener samplingPeriod=66667us batchingPeriod=100000us
14:48:14 + 0x00000007 pid= 2480 uid= 1000 package=miui.util.ProximitySensorWrapper samplingPeriod=0us batchingPeriod=0us
14:48:11 + 0x00000008 pid= 2288 uid= 1000 package=hidl_client_pid_880 samplingPeriod=500000us batchingPeriod=0us
--------- 0.035s was the duration of dumpsys sensorservice, ending at: 2019-02-11 14:58:37

最后會打印出一些最近的注冊信息,可以清晰地看到相關服務的啟動時間、pid、uid、采樣時間以及批處理時間。整個dumpsys sensorservices也就宣告結束。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM