本文已参与「新人创作礼」活动,一起开启掘金创作之路。
1、为什么需要arm汇编代码对应的机器码
在对一些apk的.so库文件的汇编代码分析过程中,经常需要修改其跳转指令,来协助分析其流程。
arm32位与arm64位库的汇编指令也是不一样的,特此整理以下常用的汇编指令对应的机器码,方便查阅。
2、arm32位空指令
arm32空指令NOP机器码: 00 00 A0 E1
00 00 A0 E1 NOP
01 10 A0 E1 MOV R1, R1
00 00 80 E2 MOV R0, R0
00 10 80 E2 MOV R1, R0
01 00 80 E2 ADD R0, R0, #1
01 10 81 E2 ADD R1, R1, #1
00 00 50 E1 CMP R0, R0
00 00 50 E3 CMP R0, #0
01 00 50 E3 CMP R0, #1
01 00 50 E1 CMP R0, R1
01 00 A0 E3 MOV R0, #1
3、给R0寄存器复制的指令
00 20 MOVS R0, #0
91 42 CMP R1, R2
18 BF IT NE
01 20 MOVNE R0, #1
70 47 BX LR
01 20 MOVS R0, #1
4、arm64位空指令的替代指令
arm64空指令NOP: 64位没有空指令,可以用MOV X0,X0 来代替,机器码:E0 03 00 AA
或者机器码:00 00 00 91
E0 03 00 AA MOV X0, X0
E1 03 01 AA MOV X1, X1
00 00 00 91 ADD X0, X0, #0
00 04 00 91 ADD X0, X0, #1
1F 00 00 F1 CMP X0, #0
1F 04 00 F1 CMP X0, #1
1F 00 01 EB CMP X0, X1
20 00 80 D2 MOV X0, #1
E0 03 00 32 MOV W0, #1
31 个R0 ~ R30,每个寄存器可以存取一个 64 位大小的数。 当使用 x0 - x30访问时,是一个 64位的数;当使用 w0 - w30访问时,是一个 32 位的数,访问的是寄存器的 低 32 位。
5、用汇编源代码生成arm32位汇编代码
(1)、arm汇编源码文件 hello.s
.data
/* Data segment: define our message string and calculate its length. */
msg:
.ascii "Hello,Arm,mov add, cmp, nop. Writtey by Appninja.\n"
len = . - msg
.text
/* Our application's entry point. */
.globl _start
_start:
/* syscall write(int fd, const void *buf, size_t count) */
mov %r0, %r0
mov %r1, %r1
add %r0, %r0,$0
add %r1, %r0,$0
add %r0, $1
add %r1, $1
cmp %r0, %r0
cmp %r0, $0
cmp %r0, $1
cmp %r0, %r1
mov %r0, $1 /* fd := STDOUT_FILENO */
ldr %r1, =msg /* buf := msg */
ldr %r2, =len /* count := len */
mov %r7, $4 /* write is syscall #4 */
swi $0 /* invoke syscall */
/* syscall exit(int status) */
mov %r0, $0 /* status := 0 */
mov %r7, $1 /* exit is syscall #1 */
swi $0 /* invoke syscall */
(2)、使用ndk工具链编译汇编源代码
进入ndk工具链目录:
AppData\Local\Android\Sdk\ndk\21.0.6113669\toolchains\arm-linux-androideabi-4.9\prebuilt\windows-x86_64\arm-linux-androideabi\bin
依次执行编译链接执行,批处理脚本如下:
as -o hello.o hello.s
ld -s -o hello hello.o
adb push hello /data/local/tmp
adb shell "chmod 777 /data/local/tmp/hello"
adb shell "ls -la /data/local/tmp/hello"
adb shell "/data/local/tmp/hello"
pause
(3)、ida反编译之后最终arm汇编代码
LOAD:00008000 ; Format : ELF for ARM (Executable)
LOAD:00008000 ; Imagebase : 8000
LOAD:00008000 ;
LOAD:00008000 ; Options : EF_ARM_SOFT_FLOAT
LOAD:00008000 ; EABI version: 5
LOAD:00008000 ;
LOAD:00008000
LOAD:00008000 ; Processor : ARM
LOAD:00008000 ; ARM architecture: ARMv4
LOAD:00008000 ; Target assembler: Generic assembler for ARM
LOAD:00008000 ; Byte sex : Little endian
LOAD:00008000
LOAD:00008000 ; ===========================================================================
LOAD:00008000
LOAD:00008000 ; Segment type: Pure code
LOAD:00008000 AREA LOAD, CODE, ALIGN=12
LOAD:00008000 ; ORG 0x8000
LOAD:00008000 CODE32
LOAD:00008000 7F 45 4C 46 dword_8000 DCD 0x464C457F ; DATA XREF: LOAD:0000803C↓o
LOAD:00008000 ; File format: \x7FELF
LOAD:00008004 01 DCB 1 ; File class: 32-bit
LOAD:00008005 01 DCB 1 ; Data encoding: little-endian
LOAD:00008006 01 DCB 1 ; File version
LOAD:00008007 00 DCB 0 ; OS/ABI: UNIX System V ABI
LOAD:00008008 00 DCB 0 ; ABI Version
LOAD:00008009 00 00 00 00 00 00 00 DCB 0, 0, 0, 0, 0, 0, 0 ; Padding
LOAD:00008010 02 00 DCW 2 ; File type: Executable
LOAD:00008012 28 00 DCW 0x28 ; Machine: ARM
LOAD:00008014 01 00 00 00 DCD 1 ; File version
LOAD:00008018 74 80 00 00 DCD start ; Entry point
LOAD:0000801C 34 00 00 00 DCD 0x34 ; PHT file offset
LOAD:00008020 6C 01 00 00 DCD 0x16C ; SHT file offset
LOAD:00008024 00 02 00 05 DCD 0x5000200 ; Processor-specific flags
LOAD:00008028 34 00 DCW 0x34 ; ELF header size
LOAD:0000802A 20 00 DCW 0x20 ; PHT entry size
LOAD:0000802C 02 00 DCW 2 ; Number of entries in PHT
LOAD:0000802E 28 00 DCW 0x28 ; SHT entry size
LOAD:00008030 07 00 DCW 7 ; Number of entries in SHT
LOAD:00008032 06 00 DCW 6 ; SHT entry index for string table
LOAD:00008034 ; ELF32 Program Header
LOAD:00008034 ; PHT Entry 0
LOAD:00008034 01 00 00 00 DCD 1 ; Type: LOAD
LOAD:00008038 00 00 00 00 DCD 0 ; File offset
LOAD:0000803C 00 80 00 00 DCD dword_8000 ; Virtual address
LOAD:00008040 00 80 00 00 DCD 0x8000 ; Physical address
LOAD:00008044 C0 00 00 00 DCD 0xC0 ; Size in file image
LOAD:00008048 C0 00 00 00 DCD 0xC0 ; Size in memory image
LOAD:0000804C 05 00 00 00 DCD 5 ; Flags
LOAD:00008050 00 10 00 00 DCD 0x1000 ; Alignment
LOAD:00008054 ; PHT Entry 1
LOAD:00008054 01 00 00 00 DCD 1 ; Type: LOAD
LOAD:00008058 C0 00 00 00 DCD 0xC0 ; File offset
LOAD:0000805C C0 90 00 00 DCD unk_90C0 ; Virtual address
LOAD:00008060 C0 90 00 00 DCD 0x90C0 ; Physical address
LOAD:00008064 35 00 00 00 DCD 0x35 ; Size in file image
LOAD:00008068 35 00 00 00 DCD 0x35 ; Size in memory image
LOAD:0000806C 06 00 00 00 DCD 6 ; Flags
LOAD:00008070 00 10 00 00 DCD 0x1000 ; Alignment
LOAD:00008070 ; LOAD ends
LOAD:00008070
.text:00008074 ; ---------------------------------------------------------------------------
.text:00008074 ; ===========================================================================
.text:00008074
.text:00008074 ; Segment type: Pure code
.text:00008074 AREA .text, CODE
.text:00008074 ; ORG 0x8074
.text:00008074 CODE32
.text:00008074
.text:00008074 EXPORT start
.text:00008074 start ; DATA XREF: LOAD:00008018↑o
.text:00008074 00 00 A0 E1 NOP
.text:00008078 01 10 A0 E1 MOV R1, R1
.text:0000807C 00 00 80 E2 MOV R0, R0
.text:00008080 00 10 80 E2 MOV R1, R0
.text:00008084 01 00 80 E2 ADD R0, R0, #1
.text:00008088 01 10 81 E2 ADD R1, R1, #1
.text:0000808C 00 00 50 E1 CMP R0, R0
.text:00008090 00 00 50 E3 CMP R0, #0
.text:00008094 01 00 50 E3 CMP R0, #1
.text:00008098 01 00 50 E1 CMP R0, R1
.text:0000809C 01 00 A0 E3 MOV R0, #1
.text:000080A0 14 10 9F E5 LDR R1, =unk_90C0
.text:000080A4 35 20 A0 E3 MOV R2, #0x35
.text:000080A8 04 70 A0 E3 MOV R7, #4
.text:000080AC 00 00 00 EF SVC 0
.text:000080B0 00 00 A0 E3 MOV R0, #0
.text:000080B4 01 70 A0 E3 MOV R7, #1
.text:000080B8 00 00 00 EF SVC 0
.text:000080B8 ; ---------------------------------------------------------------------------
.text:000080BC C0 90 00 00 off_80BC DCD unk_90C0 ; DATA XREF: .text:000080A0↑r
.text:000080BC ; .text ends
.text:000080BC
.data:000090C0 ; ===========================================================================
.data:000090C0
.data:000090C0 ; Segment type: Pure data
.data:000090C0 AREA .data, DATA, ALIGN=0
.data:000090C0 ; ORG 0x90C0
.data:000090C0 48 unk_90C0 DCB 0x48 ; H ; DATA XREF: LOAD:0000805C↑o
.data:000090C0 ; .text:000080A0↑o ...
.data:000090C1 65 DCB 0x65 ; e
.data:000090C2 6C DCB 0x6C ; l
.data:000090C3 6C DCB 0x6C ; l
.data:000090C4 6F DCB 0x6F ; o
.data:000090C5 2C DCB 0x2C ; ,
.data:000090C6 41 DCB 0x41 ; A
.data:000090C7 72 DCB 0x72 ; r
.data:000090C8 6D DCB 0x6D ; m
.data:000090C9 2C DCB 0x2C ; ,
.data:000090CA 6D DCB 0x6D ; m
.data:000090CB 6F DCB 0x6F ; o
.data:000090CC 76 DCB 0x76 ; v
.data:000090CD 20 DCB 0x20
.data:000090CE 61 DCB 0x61 ; a
.data:000090CF 64 DCB 0x64 ; d
.data:000090D0 64 DCB 0x64 ; d
.data:000090D1 2C DCB 0x2C ; ,
.data:000090D2 20 DCB 0x20
.data:000090D3 63 DCB 0x63 ; c
.data:000090D4 6D DCB 0x6D ; m
.data:000090D5 70 DCB 0x70 ; p
.data:000090D6 2C DCB 0x2C ; ,
.data:000090D7 20 DCB 0x20
.data:000090D8 6E DCB 0x6E ; n
.data:000090D9 6F DCB 0x6F ; o
.data:000090DA 70 DCB 0x70 ; p
.data:000090DB 2E DCB 0x2E ; .
.data:000090DC 20 DCB 0x20
.data:000090DD 57 DCB 0x57 ; W
.data:000090DE 72 DCB 0x72 ; r
.data:000090DF 69 DCB 0x69 ; i
.data:000090E0 74 DCB 0x74 ; t
.data:000090E1 74 DCB 0x74 ; t
.data:000090E2 65 DCB 0x65 ; e
.data:000090E3 79 DCB 0x79 ; y
.data:000090E4 20 DCB 0x20
.data:000090E5 62 DCB 0x62 ; b
.data:000090E6 79 DCB 0x79 ; y
.data:000090E7 20 DCB 0x20
.data:000090E8 41 DCB 0x41 ; A
.data:000090E9 70 DCB 0x70 ; p
.data:000090EA 70 DCB 0x70 ; p
.data:000090EB 6E DCB 0x6E ; n
.data:000090EC 69 DCB 0x69 ; i
.data:000090ED 6E DCB 0x6E ; n
.data:000090EE 6A DCB 0x6A ; j
.data:000090EF 61 DCB 0x61 ; a
.data:000090F0 2E DCB 0x2E ; .
.data:000090F1 20 DCB 0x20
.data:000090F2 72 DCB 0x72 ; r
.data:000090F3 30 DCB 0x30 ; 0
.data:000090F4 0A DCB 0xA
.data:000090F4 ; .data ends
.data:000090F4
.data:000090F4 END start