iT邦幫忙

2026 iThome 鐵人賽

DAY 8
0

前面幾天介紹了 ELF、Assembly、Register、Stack 等基本概念。

從今天開始,就正式進入 Reverse Engineering 的分析流程。

當我們拿到一個未知 Binary 時,其實不用急著直接開 IDA 或 Ghidra。

我們可以先透過一些簡單的工具快速了解它。

這種不執行程式、只分析 Binary 本身的方法,就是:

Static Analysis


0x00 準備

先建立:

#include <stdio.h>
#include <string.h>

int main() {
    char password[32];

    printf("Password: ");
    scanf("%31s", password);

    if (strcmp(password, "shark_is_cute") == 0) {
        puts("Correct!");
    } else {
        puts("Wrong!");
    }

    return 0;
}

然後編譯:

gcc chall.c -o chall

接下來假裝我們只有 chall,不知道 Source Code 長什麼樣子。


0x01 file

拿到未知 Binary,我通常會先:

file chall

可能看到:

ELF 64-bit LSB pie executable, x86-64,
dynamically linked, not stripped

從這一行就可以知道:

  • ELF Binary
  • 64-bit
  • x86-64
  • Dynamic Linking
  • PIE
  • 是否被 Strip

其中:

not stripped

代表 Binary 還保留一些 Symbol 資訊。
這對 Reverse Engineering 來說非常有幫助。


0x02 strings

下一個很好用的工具:

strings chall

可能直接看到:

Password:
Correct!
Wrong!

這時我們甚至還沒開始看 Assembly,就已經得到很多資訊。

實際上也常搭配:

strings chall | grep -i flag

或:

strings chall | grep -i pass

快速找可疑字串。

不過要注意:

看到 String 不代表它就是真的答案。

作者也可以故意放假資訊
所以 strings 比較適合拿來找線索。


0x03 readelf

前面介紹過 ELF,現在可以直接看看 Binary 的結構。

readelf -h chall

查看 ELF Header。

例如:

Class: ELF64
Machine: Advanced Micro Devices X86-64
Entry point address: 0x1070

如果想看 Section:

readelf -S chall

可能看到:

.text
.rodata
.data
.bss
.plt
.got

其中:

.text    → Machine Code
.rodata  → Read Only Data / String
.data    → Initialized Data
.bss     → Uninitialized Data

這就是前面學過的 ELF 結構真正出現在 Binary 裡的樣子。


0x04 nm

接著可以看看 Binary 裡有哪些 Symbol:

nm chall

可能看到:

main
printf
scanf
strcmp
puts

如果程式自己寫了一個:

check_password()

那也可能直接看到:

check_password

這對 Reverse Engineer 來說是一個很明顯的線索。

例如看到:

check_password
print_flag
win
admin

通常都值得優先分析。


0x05 Strip

可以試著:

strip chall

再執行:

nm chall

可能會看到:

no symbols

原本的 Function Name 不見了。

但要注意:

Symbol 消失,不代表 Function 消失。

程式的 Machine Code 還在,只是 Function Name 被移除了。
所以 Reverse Engineering 很重要的一件事情,就是:

從程式行為重新理解每個 Function 在做什麼。


0x06 objdump

最後我們可以直接看 Assembly:

objdump -d -M intel chall

可能看到:

push rbp
mov rbp, rsp
sub rsp, 0x20

這些就是前幾天學過的 Function Prologue。

往下還可能看到:

call printf@plt
call scanf@plt
call strcmp@plt

光看到這些 Function Call,其實就可以開始推測:

顯示訊息
   ↓
讀取 Input
   ↓
比較字串
   ↓
Correct / Wrong

這就是 Static Analysis 的核心:

不一定要完全看懂每一行 Assembly,也可以先透過線索建立程式的行為模型。


0x07 Basic Static Analysis Flow

所以之後拿到未知 Binary,可以先按照:

Binary
  ↓
file
  ↓
strings
  ↓
readelf
  ↓
nm
  ↓
objdump

簡單來說:

file chall
strings chall
readelf -h chall
nm chall
objdump -d -M intel chall

透過這些工具,我們可以快速了解:

  • Binary 類型
  • Architecture
  • String
  • ELF 結構
  • Symbol
  • Assembly

再決定下一步要分析哪裡。


0x08 Static vs Dynamic Analysis

今天介紹的是:

Static Analysis

也就是:

不執行程式,直接分析 Binary。

而另一種方式是:

Dynamic Analysis

也就是在程式執行時觀察:

Register
Memory
Stack
Control Flow

例如使用:

gdb ./chall

實際 Reverse Engineering 通常會:

Static Analysis
      ↓
找到可疑位置
      ↓
Dynamic Analysis
      ↓
驗證推測

兩種方式互相搭配。


0x09 小結

今天開始正式從:

學習 Assembly

走向:

分析 Binary

學到幾個最基本的工具:

file
strings
readelf
nm
objdump

最重要的不是把 Command 背起來,而是建立一個習慣:拿到 Binary 先蒐集資訊,再決定要分析哪裡。

下一篇就來進入 GUI Disassembler:IDA/Ghidra


上一篇
Day07|Stack
下一篇
Day09|Static Analysis - IDA / Ghidra
系列文
從零開始の Binary CTF:30 天系統化學習 Rev & Pwn 共 18 篇
圖片
  熱門推薦
圖片
{{ item.channelVendor }} | {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言