zoukankan      html  css  js  c++  java
  • ARM反汇编学习

    在bin文件中,就是一条条的机器指令,每条指令4个字节。

    在ADS中打开一个.s文件,选择project->disassemble

    可以看到汇编的机器码

    汇编代码如下(ADS中的一个例程\ARM\ADSv1_2\Examples\asm\armex.s):

    AREA ARMex, CODE, READONLY ; name this block of code

    ENTRY ; mark first instruction

    ; to execute

    start

    MOV r0, #10 ; Set up parameters

    MOV r1, #3

    ADD r0, r0, r1 ; r0 = r0 + r1

    stop

    MOV r0, #0x18 ; angel_SWIreason_ReportException

    LDR r1, =0x20026 ; ADP_Stopped_ApplicationExit

    SWI 0x123456 ; ARM semihosting SWI

    END ; Mark end of file

    执行project->disassemble后:

    ** Section #1 'ARMex' (SHT_PROGBITS) [SHF_ALLOC + SHF_EXECINSTR + SHF_ENTRYSECT]

    Size : 28 bytes (alignment 4)

    start

    $a

    ARMex

    0x00000000: e3a0000a .... MOV r0,#0xa

    0x00000004: e3a01003 .... MOV r1,#3

    0x00000008: e0800001 .... ADD r0,r0,r1

    stop

    0x0000000c: e3a00018 .... MOV r0,#0x18

    0x00000010: e59f1000 .... LDR r1,0x18

    0x00000014: ef123456 V4.. SWI 0x123456

    $d

    0x00000018: 00020026 &... DCD 131110

    使用UltraEdit看bin文件如下:

    clip_image002

    可以看到,与上面的一样。

    其中MOV的机器码如下(ARM体系结构pdf:p156):

    clip_image004

    cond,AL(Always)为0b1110

    最后有一个131110不知道是什么意思。

    @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@

    %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

    另一个例子汇编代码如下(ADS中的一个例程\ARM\ADSv1_2\Examples\asm\ subrout.s):

    AREA subrout, CODE, READONLY ; name this block of code

    ENTRY ; mark first instruction

    ; to execute

    start

    MOV r0, #10 ; Set up parameters

    MOV r1, #3

    BL doadd ; Call subroutine

    stop

    MOV r0, #0x18 ; angel_SWIreason_ReportException

    LDR r1, =0x20026 ; ADP_Stopped_ApplicationExit

    SWI 0x123456 ; ARM semihosting SWI

    doadd

    ADD r0, r0, r1 ; Subroutine code

    MOV pc, lr ; Return from subroutine.

    END ; Mark end of file

    执行project->disassemble后:

    ** Section #1 'subrout' (SHT_PROGBITS) [SHF_ALLOC + SHF_EXECINSTR + SHF_ENTRYSECT]

    Size : 36 bytes (alignment 4)

    start

    $a

    subrout

    0x00000000: e3a0000a .... MOV r0,#0xa

    0x00000004: e3a01003 .... MOV r1,#3

    0x00000008: ebfffffe .... BL doadd ; 0x18

    stop

    0x0000000c: e3a00018 .... MOV r0,#0x18

    0x00000010: e59f1008 .... LDR r1,0x20

    0x00000014: ef123456 V4.. SWI 0x123456

    doadd

    0x00000018: e0800001 .... ADD r0,r0,r1

    0x0000001c: e1a0f00e .... MOV pc,r14

    $d

    0x00000020: 00020026 &... DCD 131110

    使用UltraEdit看bin文件如下:

    clip_image006

    不知道为什么,ADS里面的BL doadd的机器码和bin中的机器码不一样。

    BL的机器指令如下:

    0x00000008: ebfffffe .... BL doadd ; 0x18

    clip_image008

    clip_image010

    按bin中的机器码,EB000002,1110_1101_0000_0000____0000_0000_0000_0010

    会在执行bl指令时的PC后面加上2*4byte,正好跳过3条指令。

    @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@

    %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

    下面这个例子将doadd写到另一个.s文件中。

    clip_image012

    subrout.s文件:

    AREA subrout, CODE, READONLY ; name this block of code

    ENTRY ; mark first instruction

    ; to execute

    IMPORT doadd ; import

    start

    MOV r0, #10 ; Set up parameters

    MOV r1, #3

    BL doadd ; Call subroutine

    stop

    MOV r0, #0x18 ; angel_SWIreason_ReportException

    LDR r1, =0x20026 ; ADP_Stopped_ApplicationExit

    SWI 0x123456 ; ARM semihosting SWI

    END ; Mark end of file

    fun.s文件:

    AREA subrout, CODE, READONLY ; name this block of code

    EXPORT doadd

    doadd FUNCTION

    ADD r0, r0, r1 ; Subroutine code

    MOV pc, lr ; Return from subroutine.

    ENDFUNC

    LTORG

    END

    UE查看bin结果:

    clip_image014

    可以看出,跳转指令变为跳转3个指令,doadd函数放在了bin的最后。

    @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@

    %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

    这个例子将上面的subrout.s文件改为(工程subroutprj_2F_DCD):

    AREA subrout, CODE, READONLY ; name this block of code

    ENTRY ; mark first instruction

    ; to execute

    IMPORT doadd ; import

    start

    LDR r0, Param1 ; Set up parameters

    LDR r1, Param2

    BL doadd ; Call subroutine

    stop

    MOV r0, #0x18 ; angel_SWIreason_ReportException

    LDR r1, =0x20026 ; ADP_Stopped_ApplicationExit

    SWI 0x123456 ; ARM semihosting SWI

    Param1 DCD 10

    Param2 DCD 3

    END ; Mark end of file

    MOV只能操作reg和立即数

    操作内存,MOV要改为LDR

    UE查看bin为:

    clip_image016

    LDR r0, Param1的机器码为:

    E59F0010=0111_0101_1001_1111_0000_0000_0001_0000

    Rn为R15=PC,Rd=R0,address=16(4*Instruction)+PC

    clip_image018

    输出的Image Symbol Table为:

    ================================================================================

    Image Symbol Table

    Mapping Symbols

    Sym Value Execution Region

    $a 0x00000000 ER_RO

    $d 0x00000020 ER_RO

    其中$a表示ARM Code,$d表示Data

    这是整个bin文件的区域分配,从0开始为ARM Code,然后从20开始为Data,其中ARM Code是fun section和subrout section合在一起的,Data也是两个数据合在一起的(似乎是armlink把input section中同一属性的段合并到output section中)。

    clip_image019

    ADS中输出调试信息
    clip_image021Image Map
    Symbol
    Section cross-reference
    在list file中choose一个文件,比如boot270.txt,可以把信息输出到txt中

    下面这个输出是subroutprj_2F_DCD的输出,在arm反汇编.doc里。

    ================================================================================

    Image Symbol Table

    Mapping Symbols

    Sym Value Execution Region

    $a 0x00000000 ER_RO

    $d 0x00000020 ER_RO

    Local Symbols

    Symbol Name Value Ov Type Size Object(Section)

    E:\dsparm\pxa270\project\subroutprj_2F_DCD\subrout.s 0x00000000 Number 0 subrout.o ABSOLUTE

    <Anonymous Symbol> 0x00000000 Data 16 subrout.o(.debug_abbrev)

    <Anonymous Symbol> 0x00000000 Data 128 subrout.o(.debug_info)

    <Anonymous Symbol> 0x00000000 Data 108 subrout.o(.debug_line)

    subrout 0x00000008 ARM Code 36 subrout.o(subrout)

    start 0x00000008 ARM Code 0 subrout.o(subrout)

    stop 0x00000014 ARM Code 0 subrout.o(subrout)

    Param1 0x00000020 Data 4 subrout.o(subrout)

    Param2 0x00000024 Data 4 subrout.o(subrout)

    E:\dsparm\pxa270\project\subroutprj_2F_DCD\fun.s 0x00000000 Number 0 fun.o ABSOLUTE

    <Anonymous Symbol> 0x00000000 Data 60 fun.o(.debug_frame)

    <Anonymous Symbol> 0x00000010 Data 16 fun.o(.debug_abbrev)

    fun 0x00000000 ARM Code 8 fun.o(fun)

    <Anonymous Symbol> 0x0000006c Data 96 fun.o(.debug_line)

    <Anonymous Symbol> 0x00000080 Data 124 fun.o(.debug_info)

    Global Symbols

    Symbol Name Value Ov Type Size Object(Section)

    BuildAttributes$$ARM_ISAv4$M$PE$A:L22$X:L11$S22$~IW$~STKCKD$~SHL$OSPACE 0x00000000 Number 0 anon$$obj.o ABSOLUTE

    doadd 0x00000000 ARM Code 8 fun.o(fun)

    UE查看bin结果

    clip_image023

    从bin看到,doadd两条指令放在了bin的最前面,这样

    start的值value为0x00000008

    fun的值value为0x00000000

    start和fun都是ARM Code,是代码的标号label,标号的值代表一个地址,所以start和fun在bin中的地址即为它们的值。

    Image Symbol Table中包含两部分,Local Symbol和Global Symbol,前者在只能在定义的文件中引用,后者可以在整个工程中引用。在这个工程中后者只有doadd函数。

    ========================================================================

    Memory Map of the image

    Image Entry point : 0x00000000

    Load Region LR_1 (Base: 0x00000000, Size: 0x0000002c, Max: 0xffffffff, ABSOLUTE)

    Execution Region ER_RO (Base: 0x00000000, Size: 0x0000002c, Max: 0xffffffff, ABSOLUTE)

    Base Addr Size Type Attr Idx E Section Name Object

    0x00000000 0x00000008 Code RO 5 * fun fun.o

    0x00000008 0x00000024 Code RO 1 * subrout subrout.o

    Execution Region ER_RW (Base: 0x0000002c, Size: 0x00000000, Max: 0xffffffff, ABSOLUTE)

    **** No section assigned to this execution region ****

    Execution Region ER_ZI (Base: 0x0000002c, Size: 0x00000000, Max: 0xffffffff, ABSOLUTE)

    **** No section assigned to this execution region ****

    Image Entry point : 0x00000000这句话有点问题??!!

    Base Addr Size Type Attr Idx E Section Name Object

    0x00000000 0x00000008 Code RO 5 * fun fun.o

    0x00000008 0x00000024 Code RO 1 * subrout subrout.o

    上面这些说明了各段的基地址,长度,类型(code,data),属性(RO,RW),段名,存在的目标文件。

    在这里fun放在了subrout的前面,由于armlinker在链接input section的时候排序sort是有规则的,先同一属性(RO,RW,RI),然后按名字的字母表顺序。由于fun和subrout都是RO,所以按名字fun在前面。

    -----------------------------------------------------------------

    下面以boot270工程为例子分析:

    输出的Image Symbol Table

    Global Symbols

    Symbol Name Value Ov Type Size Object(Section)

    xlli_read_SCR 0xa000cea0 ARM Code 420 xlli_LowLev_Init.o(text)

    可以看出xlli_read_SCR为ARM Code,是一个标号label,值即为其在bin中的地址,由于设置RO Base为0xA0000000,所以在bin中找0x0000cea0处的指令:

    clip_image025

    指令为E59F_419C,即为

    xlli_read_SCR FUNCTION

    ;

    ; Insure the RDH and PH bits on PXA27x must be clear to enable GPIO pins.

    ; They are sticky bits so they must be set to clear them.

    ;

    ldr r4, =xlli_PMRCREGS_PHYSICAL_BASE

    该指令表示(E表示AL,无条件,F为R15=PC,4表示放到R4里,地址为PC+19C=D03C,再加2*4为D044)

    clip_image027

    0x0000d044处的数据为40F00000,与代码中的数据吻合:

    ; POWER MANAGER base address and register offsets from the base address

    ;

    xlli_PMRCREGS_PHYSICAL_BASE EQU 0x40F00000

    这个数据在Image Symbol Table中也能找到,在Local Symbols中:

    xlli_PMRCREGS_PHYSICAL_BASE 0x40f00000 Number 0 main_Flash.o ABSOLUTE

    能看到是一个Number,值value为0x40f00000。

    这个数据的地址在Image Symbol Table中也能看到:

    Mapping Symbols

    Sym Value Execution Region

    $d 0xa000d044 ER_RO

    $d表示数据data。

    下一条指令:

    ; Get, and save the present GPIO settings for direction registers 0, 1 and 2

    ;

    ldr r4, =xlli_GPIOREGS_PHYSICAL_BASE ; Get the GPIO registers base address

    clip_image029

    指令为:E5_9F_4_194

    数据的地址为:PC+194+2*4=D048

    clip_image031

    数据为:40E0 0000,与代码中的定义对应:

    ; GENERAL PURPOSE I/O (GPIO) base address and register offsets from the base address

    ;

    xlli_GPIOREGS_PHYSICAL_BASE EQU 0x40E00000

    地址0x0000 D048在Image Symbol Table中没有,不过有:

    Mapping Symbols

    Sym Value Execution Region

    $d 0xa000d044 ER_RO

    说明从0xa000d044处开始为许多RO data

    上面的工程只有RO,怎么才能产生RW,RI呢?

    MOV E3

    LDR E5

    ADD E0

  • 相关阅读:
    hdu2243 考研路茫茫——单词情结【AC自动机】【矩阵快速幂】
    poj3376 Finding Palindromes【exKMP】【Trie】
    hdu4763 Theme Section【next数组应用】
    hdu2609 How many【最小表示法】【Hash】
    hdu3374 String Problem【最小表示法】【exKMP】
    poj2728 Desert King【最优比率生成树】【Prim】【0/1分数规划】
    python装饰器
    python面试题
    salt教程1-理解saltstack
    redis慢查询日志
  • 原文地址:https://www.cnblogs.com/yanhc/p/2175280.html
Copyright © 2011-2022 走看看