2011年6月30日 星期四

How to use gdb to debug Android native c /c++ code.

如何使用GDB debug Android native c/c++ code
假設你的target device(Android手機或平板電腦) 跟你的Linux電腦主機之間已經用usb連線,而且target device 已經將"USB debugging" 打開
1.(host) $android_root/out/host/linux-x86/bin/adb forward tcp:1234 tcp:1234
  (使他們之間用port 1234溝通)

2. (host)$android_root/out/host/linux-x86/bin/adb shell
    (接下來就連到target端)

3.(target)#gdbserver :1234 --attach YOUR_PID
   (你可以使用 cat /proc/YOUR_PID/maps | grep YOUR_LIBRARY 去查看你要debug的library是不是在該PID裡面)
   (如果成功attach上,你可以看到
     Attached; pid = xxx
      Listening on port 1234
    的訊息)

4. 在host端要使用 $android_root/prebuilt/linux-x86/toolchain/arm-linux-androideabi-4.4.x/bin/arm-linux-androideabi-gdb , 不要使用NDK所附的arm-linux-androideabi-gdb.

5.在host端再開一個console,因為前一個console已經連到target端無法再使用囉
(host) $ ./arm-linux-androideabi-gdb  (假設你已經在$android_root/prebuilt/linux-x86/toolchain/arm-linux-androideabi-4.4.x/bin目錄下)

6. android 沒有strip過的 libraries 是放在   
  $android_root/out/target/product/YOUR_PRODUCT_NAME/symbols/system/lib 下
  而執行檔是放在$android_root/out/target/product/YOUR_PRODUCT_NAME/symbols/system/bin 下

7.(host) (gdb) target remote  :1234 
    (這是告訴gdb要跟remote端 的1234 port做連接, 這時候在target端的gdbserver會出現 Remote debugging from host 127.0.0.1 這就表示gdb與gdbserver已經連上線囉)

8.(host)(gdb) set solib-search-path $android_root/out/target/product/YOUR_PRODUCT_NAME/symbols/system/lib/:
$android_root/out/target/product/YOUR_PRODUCT_NAME/symbols/system/bin/
     (這是告訴gdb要在哪找相對應的debug symbol,這時候你應該可以看到gdb在load debug symbol )

9.如果你要debug InputDispatcher::notifyMotion  in InputDispatcher.cpp 你可以使用下述方法
  (host)(gdb)b android::InputDispatcher::notifyMotion 
  (你也可以使用Tab鍵 幫你省去打字的困擾, 當然啦,也可以利用Tab鍵得知gdb是否已正確找到你要設break point的點的debug symbol. 因為InputDispatcher.cpp在檔案開頭有加上namespace andeoid{}去包code,所以在找function時要把namespace加上去 , namespace::class_name::function_name)

10.(host)(gdb) c
    (讓被attached的process繼續跑下去)

11.這時候你去觸碰screen,就會觸動這break point

12.(host)(gdb)detach
     (釋放被attached的process)

13.(host)(gdb)quit
     (離開gdb)