為什么要反匯編?反匯編文件的生成和解讀

2023-08-02 10:21:30 來源:芯片逆向

為什么要反匯編

反匯編顧名思義就是匯編的逆過程,將二進制文件反匯編成匯編代碼。arm-linux-objdump是交叉編譯工具鏈里的一個工具,專門用來反匯編的,將二進制代碼反匯編成匯編代碼來查看。


(資料圖片僅供參考)

為什么要反匯編

1.逆向破解。將可執行程序反匯編得到匯編代碼,再根據匯編代碼推理出整個程序的邏輯。這個不是一般人能做的,能看懂大量匯編語言寫的程序都很困難了,更別說反推別人的代碼邏輯。

2.調試程序時可以幫助我們理解并檢測生成的可執行程序是否正常,尤其是在理解鏈接腳本和鏈接地址等概念時。

3.C語言的源代碼編譯鏈接生成的可執行文件再反匯編,可以幫助我們理解C語言和匯編語言的對應關系,有助于深入理解C語言。

反匯編文件的生成和解讀

反匯編文件的生成:

上面是一個簡單的Makefile,功能是把源文件.S和.c先編譯成.o文件,再把.o文件鏈接成.elf的可執行文件。arm-linux-objdump -D led.elf > led_elf.dis是將led.elf反匯編成ed_elf.dis。

源文件:star.s是一個匯編文件

star.s是一個學習S5PV210開發板時點亮LED的匯編程序,由開始、點亮、延時和死循環組成,在這里并不關注具體實現的功能,重點是和反匯編生成的文件進行對照。

得到的反匯編文件:led_elf.dis

解析:

1.第一行:led.elf: file format elf32-littlearm。表明此匯編程序是由led.elf生成,程序是32的小端模式。

2.00000000 <_start>:前面的00000000是標號的地址,<_start>是標號,對應start.s的_start標號。其實標號就相當于C語言中的函數名,在C語言中也可以用函數名代表函數的首地址,在這里可以得到印證。反匯編的標號就是由匯編文件得來的,這樣可以方便我們找到反匯編文件和匯編文件對應的部分。

3.整個反匯編文件分為三列,分別對應:指令地址、指令機器碼、指令機器碼反匯編到的指令。

我們在這里對匯編文件的前幾句進行解讀:

1.ldr r1, [pc, #112]:此句對應于匯編文件的ldr r1, =0xE0200240。功能是將0xE0200240存到r1寄存器中。[pc, #112]代表pc+70地址處的數據(#112是十進制),此時PC指向的是當前地址的下兩級,就是pc = 0 + 8,于是pc + 70 = 78。78地址處存放的數據就是e0200240,剛好等于匯編語句要加載的數據0xE0200240。所以ldr r1, [pc, #112]和ldr r1, =0xE0200240實現的是同樣的功能。

2.ldr r0, [pc, #112]對應于匯編文件的ldr r0, =0x00111000。解讀的方式和上面一致,只是要注意此時PC= 4 + 8。

3. str r0, [r1]語句匯編語句和反匯編語句是一致的。

4. mov r2, #4096對應于匯編的mov r2, #0x1000,兩者是相同的,十進制的4096等于十六進制的0x1000。

補充:1.PC指向當前地址的前兩級是因為流水線的存在,不同型號的ARM芯片流水線的級數是不同的,但是在反匯編文件里為了統一,都是按照3級流水線處理。

2.為什么向寄存器加載數據,有的是直接加載(mov r2, #4096),有的要用相對尋址的方式加載(ldr r1, [pc, #112])?這里涉及到合法立即數和非法立即數,簡單來書就是數據太大,一條語句的數據部分表達不了,于是就將要加載的數據放在某個地址處,要用到的時候就去該地址處取,此時的ldr也是偽指令。

審核編輯:湯梓紅

標簽:

上一篇:分享三個小夜燈電路圖 小夜燈電路的工作原理
下一篇:最后一頁