2014-10-10 82 views
1

軟件:官方TI android版本(源代碼包),Jelly bean 4.2.2 for AM335x,(是的,arago/rowboat/TI開發者添加了對香草aosp的修改,但與我的問題無關。)原生Android GDB遠程調試得到了SIGILL

硬件:基於AM335x Cortex A8的SOC am335xevm_sk(TI的開發booard)

我做什麼:

  1. 建立系統,並使用SD卡來引導硬件。一切正常。

  2. adb拉出init.am335xevm.rc文件,註釋掉rild服務並推回去,重啓目標系統。我這樣做是因爲我想使用交叉調試器來遠程調試rild。

  3. 設置遠程調試:adb轉發tcp端口。並啓動gdbserver的目標系統上,如:

    [email protected]:/ # gdbserver localhost:2345 system/bin/rild 
    Process system/bin/rild created; pid = 829 
    Listening on port 2345 
    Remote debugging from host 127.0.0.1 
    
  4. 遠程調試RILD,如:

    [email protected]:~/devkit/JB422$ PATH=$PATH:/home/ma/devkit/JB422/prebuilts/gcc/linux-x86/arm/arm-linux-androideabi-4.6/bin 
    [email protected]:~/devkit/JB422$ arm-linux-androideabi-gdb 
    GNU gdb (GDB) 7.3.1-gg2 
    Copyright (C) 2011 Free Software Foundation, Inc. 
    License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html> 
    This is free software: you are free to change and redistribute it. 
    There is NO WARRANTY, to the extent permitted by law. Type "show copying" 
    and "show warranty" for details. 
    This GDB was configured as "--host=x86_64-linux-gnu --target=arm-linux-android". 
    For bug reporting instructions, please see: 
    <xxxx://www.gnu.org/software/gdb/bugs/>. 
    (gdb) file /home/ma/devkit/JB422/out/target/product/am335xevm_sk/symbols/system/bin/rild 
    Reading symbols from /home/ma/devkit/JB422/out/target/product/am335xevm_sk/symbols/system/bin/rild...done. 
    (gdb) set sysroot /home/ma/devkit/JB422/out/target/product/am335xevm_sk/symbols 
    (gdb) target remote localhost:2345 
    Remote debugging using localhost:2345 
    __dl__start() at bionic/linker/arch/arm/begin.S:35 
    35 mov r0, sp 
    (gdb) n 
    36 mov r1, #0 
    (gdb) n 
    37 bl __linker_init 
    (gdb) n 
    
    Program received signal SIGILL, Illegal instruction. 
    0x4013a89e in __linker_init (elfdata=0xbee7bae0) at bionic/linker/linker.cpp:2030 
    2030 extern "C" unsigned __linker_init(unsigned **elfdata) { 
    (gdb) c 
    Continuing. 
    
    Program terminated with signal SIGILL, Illegal instruction. 
    The program no longer exists. 
    (gdb) 
    

~~~~~~~~~~~~~~~~~ ~~~~~~~~~~

我對低級工具鏈問題並不是很熟悉。我搜索了這個問題,似乎很少有人遇到同樣的問題。

我下載了aosp源碼(Android 4.2.2_r1,JDQ39),並比較了預建的工具鏈和NDK內容,發現沒有顯着差異。

我也試過最新的NDK(r10b)。使用NDK中的預建工具鏈來重建整個目標系統並進行調試,結果是一樣的。

我也嘗試生成平臺設置爲android-17和android-18的獨立工具鏈,並重覆上述步驟,結果是一樣的。

我也嘗試重新構建NDK工具鏈並沒有區別。

我也嘗試過更新版本的gdbserver(在NDK r10b包中預建),問題依然存在。

~~~~~~~~~~~~~~~~~~~~~~~~~~~

,但如果我使用NDK工具鏈調試一個簡單的hello-world程序(與liblog動態鏈接),如本頁面提出:

www點srombauts點FR/2011/03/06 /獨立的工具鏈/

,做調試,我可以進入主()但在程序退出後,目標系統上的進程得到了類似的SIGILL終止,而不是正常的退出。

~~~~~~~~~~~~~~~~~~~~~~~~~~~

我很困惑,爲什麼出現這種情況,因爲許多許多開發者使用gdb來調試本機代碼和谷歌平臺開發人員也應該依靠gdb大量調試。 gdb或gdbserver中的錯誤似乎不太可能。也許它與am335x內核相關且具體?或者我錯過了一些重要的使用gdb的東西?說,目標架構選項?或者應該爲這種本機調試指定某些編譯器選項?我仔細閱讀了很多關於android原生遠程調試的在線文章,並沒有發現任何特別指出的內容。

我真的想用遠程GDB調試一些本地程序,包括RIL和其他一些測試用例包裝HAL庫。請幫忙!

回答

0

對不起,這不是一個答案,但一個補充我剛纔的問題。

我進一步挖的問題。

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

我把一個基本的HelloWorld程序裏面的Android源代碼樹:

#include <stdio.h> 
#include <android/log.h> 

#define LOGI(...) ((void)__android_log_print(ANDROID_LOG_INFO, "hello-native", __VA_ARGS__)) 

void main(void) 
{ 
    printf("Hello Native Printf\n"); 
    LOGI("Hello Native LOGI"); 
} 

與Android.mk文件:

LOCAL_PATH:= $(call my-dir) 

include $(CLEAR_VARS) 

LOCAL_MODULE := hello-native 
LOCAL_MODULE_TAGS := optional 
LOCAL_SRC_FILES := hello-native.c 

LOCAL_SHARED_LIBRARIES := liblog 

include $(BUILD_EXECUTABLE) 

然後調試失敗SIGILL如前面的文章中提到。

但是,如果我用一個標準的Makefile(如由Karim Yaghmour提出了他的優秀著作嵌入式Android的,140頁):

#Paths and settings 

TARGET_PRODUCT = am335xevm_sk 
ANDROID_ROOT = /home/ma/devkit/JB422 
BIONIC_LIBC = $(ANDROID_ROOT)/bionic/libc 
PRODUCT_OUT = $(ANDROID_ROOT)/out/target/product/$(TARGET_PRODUCT) 
CROSS_COMPILE = $(ANDROID_ROOT)/prebuilts/gcc/linux-x86/arm/arm-linux-androideabi-4.6/bin/arm-linux-androideabi- 

# Tool names 
AS = $(CROSS_COMPILE)as 
AR = $(CROSS_COMPILE)ar 
CC = $(CROSS_COMPILE)gcc 
CPP = $(CC) -E 
LD = $(CROSS_COMPILE)ld 
NM = $(CROSS_COMPILE)nm 
OBJCOPY = $(CROSS_COMPILE)objcopy 
OBJDUMP = $(CROSS_COMPILE)objdump 
RANLIB = $(CROSS_COMPILE)ranlib 
READELF = $(CROSS_COMPILE)readelf 
SIZE = $(CROSS_COMPILE)size 
STRINGS = $(CROSS_COMPILE)strings 
STRIP = $(CROSS_COMPILE)strip 

export AS AR CC CPP LD NM OBJCOPY OBJDUMP RANLIB READELF \ 
SIZE STRINGS STRIP 

# Build settings 

CFLAGS = -O0 -Wall -fno-short-enums -ggdb 

HEADER_OPS = -I$(BIONIC_LIBC)/include \ 
-I$(BIONIC_LIBC)/arch-arm/include \ 
-I$(BIONIC_LIBC)/kernel/common \ 
-I$(BIONIC_LIBC)/kernel/arch-arm \ 
-I$(ANDROID_ROOT)/system/core/include 

LDFLAGS = -nostdlib -Wl,-dynamic-linker,/system/bin/linker \ 
$(PRODUCT_OUT)/obj/lib/crtbegin_dynamic.o \ 
$(PRODUCT_OUT)/obj/lib/crtend_android.o \ 
-L$(PRODUCT_OUT)/obj/lib -lc -ldl -llog 

# Installation variables 
EXEC_NAME = hello-native 
INSTALL = install 
INSTALL_DIR = $(PRODUCT_OUT)/system/bin 

# Files needed for the build 
OBJS = hello-native.o 

# Make rules 
all: hello-native 

.c.o: 
$(CC) $(CFLAGS) $(HEADER_OPS) -c $< 

hello-native: ${OBJS} 
$(CC) -o $(EXEC_NAME) ${OBJS} $(LDFLAGS) 

install: hello-native 
test -d $(INSTALL_DIR) || $(INSTALL) -d -m 755 $(INSTALL_DIR) 
$(INSTALL) -m 755 $(EXEC_NAME) $(INSTALL_DIR) 

clean: 
rm -f *.o $(EXEC_NAME) core 
distclean: 
rm -f *~ 
rm -f *.o $(EXEC_NAME) core 

然後程序編譯和調試正確。唯一的例外是程序退出時,如果我將sysroot設置爲/ out/target/product/am335xevm_sk/symbols,我得到了SIGILL,但是如果我沒有設置調試器sysroot,則程序正常退出。

他們的作品都以同樣的方式用不同的工具鏈和調試器,從原來的TI發佈,即從原來的或新版本NDK,或在NDK源代碼rebuilts。

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

然後我試圖編譯RILD在ARM代碼,與LOCAL_ARM_MODE設置爲佈防,如:

ifeq ($(TARGET_ARCH),arm) 

LOCAL_SHARED_LIBRARIES += libdl 
endif # arm 

LOCAL_CFLAGS := -DRIL_SHLIB -O0 
LOCAL_ARM_MODE := arm 

LOCAL_MODULE:= rild 
LOCAL_MODULE_TAGS := optional 

include $(BUILD_EXECUTABLE) 

然後程序編譯和調試正確,如果我不設置SYSROOT到了/目標/產品/ am335xevm_sk /符號,否則,如前所述,調試器可以使用SIGILL進入鏈接器和崩潰。

這至少對我的需要提供解決方法的解決方案,但我不能相信的Android(NDK)GDB不能處理拇指代碼?有沒有我錯過了gcc/gdb設置?或者一些gcc選項在Rowboat發行版中被修改,以防官方的gdb工具正常工作?

幫助!

+0

嗨不是專家以任何手段,但我建議創建一個簡單的例子,A​​ndroid應用程序導入一些本地代碼(編譯一些本地代碼到一個庫,然後從Java加載它),然後用NDK-GDB命令進行調試,以便了解ndk-gdb的功能。它將solib路徑設置爲包含本機庫的路徑,但它也從設備中拉出一些庫並將它們添加到solib路徑。我只有在我開始用ndk-gdb進行調試時(並且當然使用adb root),纔開始調試工作,並且沒有SIGILL的問題。 – Colin 2014-11-14 00:13:58