TOC
Open TOC
Link Lab
源
https://www.icourse163.org/course/NJU-1449521162
MOOC 的版本似乎只有四个阶段,而原版似乎有六个阶段……
编译选项
-no-pie Don't produce a dynamically linked position independent executable.
注意加上 -m32 选项
$ gcc -m32 -no-pie -o linkbomb main.o phase1.o
不如写个 makefile
.PHONY: phase1 clean
phase1: main.o phase1.o gcc -m32 -no-pie -o linkbomb main.o phase1.o ./linkbomb
clean: rm linkbomb
main
readelf
ELF Header: Magic: 7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00 Class: ELF32 Data: 2's complement, little endian Version: 1 (current) OS/ABI: UNIX - System V ABI Version: 0 Type: REL (Relocatable file) Machine: Intel 80386 Version: 0x1 Entry point address: 0x0 Start of program headers: 0 (bytes into file) Start of section headers: 852 (bytes into file) Flags: 0x0 Size of this header: 52 (bytes) Size of program headers: 0 (bytes) Number of program headers: 0 Size of section headers: 40 (bytes) Number of section headers: 13 Section header string table index: 12
Section Headers: [Nr] Name Type Addr Off Size ES Flg Lk Inf Al [ 0] NULL 00000000 000000 000000 00 0 0 0 [ 1] .text PROGBITS 00000000 000034 000040 00 AX 0 0 1 [ 2] .rel.text REL 00000000 0002cc 000020 08 I 10 1 4 [ 3] .data PROGBITS 00000000 000074 000000 00 WA 0 0 1 [ 4] .bss NOBITS 00000000 000074 000000 00 WA 0 0 1 [ 5] .rodata PROGBITS 00000000 000080 0000c4 00 A 0 0 32 [ 6] .comment PROGBITS 00000000 000144 00001d 01 MS 0 0 1 [ 7] .note.GNU-stack PROGBITS 00000000 000161 000000 00 0 0 1 [ 8] .eh_frame PROGBITS 00000000 000164 000044 00 A 0 0 4 [ 9] .rel.eh_frame REL 00000000 0002ec 000008 08 I 10 8 4 [10] .symtab SYMTAB 00000000 0001a8 0000f0 10 11 9 4 [11] .strtab STRTAB 00000000 000298 000032 00 0 0 1 [12] .shstrtab STRTAB 00000000 0002f4 00005f 00 0 0 1Key to Flags: W (write), A (alloc), X (execute), M (merge), S (strings), I (info), L (link order), O (extra OS processing required), G (group), T (TLS), C (compressed), x (unknown), o (OS specific), E (exclude), p (processor specific)
There are no section groups in this file.
There are no program headers in this file.
There is no dynamic section in this file.
Relocation section '.rel.text' at offset 0x2cc contains 4 entries: Offset Info Type Sym.Value Sym. Name00000012 00000a01 R_386_32 00000004 phase0000001b 00000a01 R_386_32 00000004 phase00000027 00000501 R_386_32 00000000 .rodata0000002c 00000e02 R_386_PC32 00000000 puts
Relocation section '.rel.eh_frame' at offset 0x2ec contains 1 entry: Offset Info Type Sym.Value Sym. Name00000020 00000202 R_386_PC32 00000000 .text
The decoding of unwind sections for machine type Intel 80386 is not currently supported.
Symbol table '.symtab' contains 15 entries: Num: Value Size Type Bind Vis Ndx Name 0: 00000000 0 NOTYPE LOCAL DEFAULT UND 1: 00000000 0 FILE LOCAL DEFAULT ABS main.c 2: 00000000 0 SECTION LOCAL DEFAULT 1 3: 00000000 0 SECTION LOCAL DEFAULT 3 4: 00000000 0 SECTION LOCAL DEFAULT 4 5: 00000000 0 SECTION LOCAL DEFAULT 5 6: 00000000 0 SECTION LOCAL DEFAULT 7 7: 00000000 0 SECTION LOCAL DEFAULT 8 8: 00000000 0 SECTION LOCAL DEFAULT 6 9: 00000000 64 OBJECT GLOBAL DEFAULT 5 zzGSwc 10: 00000004 4 OBJECT GLOBAL DEFAULT COM phase 11: 00000004 4 OBJECT GLOBAL DEFAULT COM phase_id 12: 00000040 15 OBJECT GLOBAL DEFAULT 5 challenge 13: 00000000 64 FUNC GLOBAL DEFAULT 1 main 14: 00000000 0 NOTYPE GLOBAL DEFAULT UND puts
No version information found in this file.
objdump
main.o: file format elf32-i386
Disassembly of section .text:
00000000 <main>: 0: 8d 4c 24 04 lea 0x4(%esp),%ecx 4: 83 e4 f0 and $0xfffffff0,%esp 7: ff 71 fc push -0x4(%ecx) a: 55 push %ebp b: 89 e5 mov %esp,%ebp d: 51 push %ecx e: 83 ec 04 sub $0x4,%esp 11: a1 00 00 00 00 mov 0x0,%eax 16: 85 c0 test %eax,%eax 18: 74 09 je 23 <main+0x23> 1a: a1 00 00 00 00 mov 0x0,%eax 1f: ff d0 call *%eax 21: eb 10 jmp 33 <main+0x33> 23: 83 ec 0c sub $0xc,%esp 26: 68 50 00 00 00 push $0x50 2b: e8 fc ff ff ff call 2c <main+0x2c> 30: 83 c4 10 add $0x10,%esp 33: b8 00 00 00 00 mov $0x0,%eax 38: 8b 4d fc mov -0x4(%ebp),%ecx 3b: c9 leave 3c: 8d 61 fc lea -0x4(%ecx),%esp 3f: c3 ret
main.o 中会调用相应模块 phase[n].o 中如下定义的一个全局函数指针变量 phase
void (*phase)() = do_phase;
其中,作为其初始值的 do_phase 是各阶段模块中实现的一个全局函数,用来完成该阶段的具体功能
所以似乎现在 main 没啥用
phase1 - 静态数据与 ELF 数据节
修改 .data section 的内容
readelf
ELF Header: Magic: 7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00 Class: ELF32 Data: 2's complement, little endian Version: 1 (current) OS/ABI: UNIX - System V ABI Version: 0 Type: REL (Relocatable file) Machine: Intel 80386 Version: 0x1 Entry point address: 0x0 Start of program headers: 0 (bytes into file) Start of section headers: 892 (bytes into file) Flags: 0x0 Size of this header: 52 (bytes) Size of program headers: 0 (bytes) Number of program headers: 0 Size of section headers: 40 (bytes) Number of section headers: 14 Section header string table index: 13
Section Headers: [Nr] Name Type Addr Off Size ES Flg Lk Inf Al [ 0] NULL 00000000 000000 000000 00 0 0 0 [ 1] .text PROGBITS 00000000 000034 00001a 00 AX 0 0 1 [ 2] .rel.text REL 00000000 0002f0 000010 08 I 11 1 4 [ 3] .data PROGBITS 00000000 000060 000100 00 WA 0 0 32 [ 4] .rel.data REL 00000000 000300 000010 08 I 11 3 4 [ 5] .bss NOBITS 00000000 000160 000000 00 WA 0 0 1 [ 6] .rodata PROGBITS 00000000 000160 000002 00 A 0 0 1 [ 7] .comment PROGBITS 00000000 000162 00001d 01 MS 0 0 1 [ 8] .note.GNU-stack PROGBITS 00000000 00017f 000000 00 0 0 1 [ 9] .eh_frame PROGBITS 00000000 000180 000038 00 A 0 0 4 [10] .rel.eh_frame REL 00000000 000310 000008 08 I 11 9 4 [11] .symtab SYMTAB 00000000 0001b8 000100 10 12 12 4 [12] .strtab STRTAB 00000000 0002b8 000038 00 0 0 1 [13] .shstrtab STRTAB 00000000 000318 000063 00 0 0 1Key to Flags: W (write), A (alloc), X (execute), M (merge), S (strings), I (info), L (link order), O (extra OS processing required), G (group), T (TLS), C (compressed), x (unknown), o (OS specific), E (exclude), p (processor specific)
There are no section groups in this file.
There are no program headers in this file.
There is no dynamic section in this file.
Relocation section '.rel.text' at offset 0x2f0 contains 2 entries: Offset Info Type Sym.Value Sym. Name00000007 00000301 R_386_32 00000000 .data00000010 00000e02 R_386_PC32 00000000 puts
Relocation section '.rel.data' at offset 0x300 contains 2 entries: Offset Info Type Sym.Value Sym. Name0000003c 00000601 R_386_32 00000000 .rodata000000fc 00000d01 R_386_32 00000000 do_phase
Relocation section '.rel.eh_frame' at offset 0x310 contains 1 entry: Offset Info Type Sym.Value Sym. Name00000020 00000202 R_386_PC32 00000000 .text
The decoding of unwind sections for machine type Intel 80386 is not currently supported.
Symbol table '.symtab' contains 16 entries: Num: Value Size Type Bind Vis Ndx Name 0: 00000000 0 NOTYPE LOCAL DEFAULT UND 1: 00000000 0 FILE LOCAL DEFAULT ABS phase1.c 2: 00000000 0 SECTION LOCAL DEFAULT 1 3: 00000000 0 SECTION LOCAL DEFAULT 3 4: 00000000 0 SECTION LOCAL DEFAULT 5 5: 00000000 60 OBJECT LOCAL DEFAULT 3 IOcgnr 6: 00000000 0 SECTION LOCAL DEFAULT 6 7: 00000040 187 OBJECT LOCAL DEFAULT 3 OdZAJybs 8: 000000fb 1 OBJECT LOCAL DEFAULT 3 FUGsLK 9: 00000000 0 SECTION LOCAL DEFAULT 8 10: 00000000 0 SECTION LOCAL DEFAULT 9 11: 00000000 0 SECTION LOCAL DEFAULT 7 12: 0000003c 4 OBJECT GLOBAL DEFAULT 3 phase_id 13: 00000000 26 FUNC GLOBAL DEFAULT 1 do_phase 14: 00000000 0 NOTYPE GLOBAL DEFAULT UND puts 15: 000000fc 4 OBJECT GLOBAL DEFAULT 3 phase
No version information found in this file.
objdump
phase1.o: file format elf32-i386
Disassembly of section .text:
00000000 <do_phase>: 0: 55 push %ebp 1: 89 e5 mov %esp,%ebp 3: 83 ec 08 sub $0x8,%esp 6: b8 79 00 00 00 mov $0x79,%eax b: 83 ec 0c sub $0xc,%esp e: 50 push %eax f: e8 fc ff ff ff call 10 <do_phase+0x10> 14: 83 c4 10 add $0x10,%esp 17: 90 nop 18: c9 leave 19: c3 ret
这一阶段比较简单,先介绍暴力方法,先观察默认的输出:
uh Xlsly tUcYqD8AJBKqcGvAALrTuUiXUzOdbcIlIoUCERLgN5 q FKgQDngkZg32zwxuJ8z1cd owMmQkYOxjb1wAu0zpyjX tv8KMwbS6BGydD2aDG69UIIES5Fa
然后定位 phase1.o 中这段字符串的位置,起始在 0xd9,暴力修改为:
30 38 30 39 4e 4a 55 30 36 34 00
即 0809NJU064,即可……
查看和修改二进制文件:
$ vi -b phase1.o然后切换到十六进制模式:
:%!xxd修改完后切换回来
:%!xxd -r最后保存即可
下面介绍正常的方法,注意到 IA-32 使用栈来传递参数,我们定位 phase1.o 的反汇编
6: b8 79 00 00 00 mov $0x79,%eax b: 83 ec 0c sub $0xc,%esp e: 50 push %eax f: e8 fc ff ff ff call 10 <do_phase+0x10>
可以传递给 puts 函数的参数为 0x79
至于为什么是 puts 函数,观察 .rel.text 知在 .text section 偏移 0x10 的地方有一个重定位表项,其名字为 puts
猜测
fc ff ff ff
是为了在重定位时弥补 PC + 4IA-32 和 x86-64 似乎有略微不同
而 .data section 在 ELF 文件中的偏移为 0x60,两者相加立得 0xd9
可以通过反汇编可执行文件 linkbomb 进一步观察:
080491b6 <do_phase>: 80491b6: 55 push %ebp 80491b7: 89 e5 mov %esp,%ebp 80491b9: 83 ec 08 sub $0x8,%esp 80491bc: b8 b9 c0 04 08 mov $0x804c0b9,%eax 80491c1: 83 ec 0c sub $0xc,%esp 80491c4: 50 push %eax 80491c5: e8 76 fe ff ff call 8049040 <puts@plt> 80491ca: 83 c4 10 add $0x10,%esp 80491cd: 90 nop 80491ce: c9 leave 80491cf: c3 ret
phase2 - 指令与 ELF 代码节
修改 .text section 的内容
readelf
ELF Header: Magic: 7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00 Class: ELF32 Data: 2's complement, little endian Version: 1 (current) OS/ABI: UNIX - System V ABI Version: 0 Type: REL (Relocatable file) Machine: Intel 80386 Version: 0x1 Entry point address: 0x0 Start of program headers: 0 (bytes into file) Start of section headers: 1012 (bytes into file) Flags: 0x0 Size of this header: 52 (bytes) Size of program headers: 0 (bytes) Number of program headers: 0 Size of section headers: 40 (bytes) Number of section headers: 14 Section header string table index: 13
Section Headers: [Nr] Name Type Addr Off Size ES Flg Lk Inf Al [ 0] NULL 00000000 000000 000000 00 0 0 0 [ 1] .text PROGBITS 00000000 000034 000116 00 AX 0 0 1 [ 2] .rel.text REL 00000000 000348 000020 08 I 11 1 4 [ 3] .data PROGBITS 00000000 00014c 000008 00 WA 0 0 4 [ 4] .rel.data REL 00000000 000368 000010 08 I 11 3 4 [ 5] .bss NOBITS 00000000 000154 000000 00 WA 0 0 1 [ 6] .rodata PROGBITS 00000000 000154 00000a 00 A 0 0 1 [ 7] .comment PROGBITS 00000000 00015e 00001d 01 MS 0 0 1 [ 8] .note.GNU-stack PROGBITS 00000000 00017b 000000 00 0 0 1 [ 9] .eh_frame PROGBITS 00000000 00017c 000078 00 A 0 0 4 [10] .rel.eh_frame REL 00000000 000378 000018 08 I 11 9 4 [11] .symtab SYMTAB 00000000 0001f4 000110 10 12 10 4 [12] .strtab STRTAB 00000000 000304 000043 00 0 0 1 [13] .shstrtab STRTAB 00000000 000390 000063 00 0 0 1Key to Flags: W (write), A (alloc), X (execute), M (merge), S (strings), I (info), L (link order), O (extra OS processing required), G (group), T (TLS), C (compressed), x (unknown), o (OS specific), E (exclude), p (processor specific)
There are no section groups in this file.
There are no program headers in this file.
There is no dynamic section in this file.
Relocation section '.rel.text' at offset 0x348 contains 4 entries: Offset Info Type Sym.Value Sym. Name00000074 00000c02 R_386_PC32 00000000 strlen000000aa 00000501 R_386_32 00000000 .rodata000000b2 00000d02 R_386_PC32 00000000 strcmp000000c4 00000e02 R_386_PC32 00000000 puts
Relocation section '.rel.data' at offset 0x368 contains 2 entries: Offset Info Type Sym.Value Sym. Name00000000 00000501 R_386_32 00000000 .rodata00000004 00000f01 R_386_32 000000d0 do_phase
Relocation section '.rel.eh_frame' at offset 0x378 contains 3 entries: Offset Info Type Sym.Value Sym. Name00000020 00000202 R_386_PC32 00000000 .text00000040 00000202 R_386_PC32 00000000 .text00000060 00000202 R_386_PC32 00000000 .text
The decoding of unwind sections for machine type Intel 80386 is not currently supported.
Symbol table '.symtab' contains 17 entries: Num: Value Size Type Bind Vis Ndx Name 0: 00000000 0 NOTYPE LOCAL DEFAULT UND 1: 00000000 0 FILE LOCAL DEFAULT ABS phase2.c 2: 00000000 0 SECTION LOCAL DEFAULT 1 3: 00000000 0 SECTION LOCAL DEFAULT 3 4: 00000000 0 SECTION LOCAL DEFAULT 5 5: 00000000 0 SECTION LOCAL DEFAULT 6 6: 000000a0 48 FUNC LOCAL DEFAULT 1 AFPQyOcF 7: 00000000 0 SECTION LOCAL DEFAULT 8 8: 00000000 0 SECTION LOCAL DEFAULT 9 9: 00000000 0 SECTION LOCAL DEFAULT 7 10: 00000000 4 OBJECT GLOBAL DEFAULT 3 phase_id 11: 00000000 160 FUNC GLOBAL DEFAULT 1 nndZqWCYPw 12: 00000000 0 NOTYPE GLOBAL DEFAULT UND strlen 13: 00000000 0 NOTYPE GLOBAL DEFAULT UND strcmp 14: 00000000 0 NOTYPE GLOBAL DEFAULT UND puts 15: 000000d0 70 FUNC GLOBAL DEFAULT 1 do_phase 16: 00000004 4 OBJECT GLOBAL DEFAULT 3 phase
No version information found in this file.
objdump
phase2.o: file format elf32-i386
Disassembly of section .text:
00000000 <nndZqWCYPw>: 0: 55 push %ebp 1: 89 e5 mov %esp,%ebp 3: 83 ec 48 sub $0x48,%esp 6: c7 45 bb 70 76 78 32 movl $0x32787670,-0x45(%ebp) d: c7 45 bf 55 37 6b 78 movl $0x786b3755,-0x41(%ebp) 14: c7 45 c3 6b 4a 37 54 movl $0x54374a6b,-0x3d(%ebp) 1b: c7 45 c7 51 20 45 64 movl $0x64452051,-0x39(%ebp) 22: c7 45 cb 79 59 45 6e movl $0x6e455979,-0x35(%ebp) 29: c7 45 cf 49 72 73 61 movl $0x61737249,-0x31(%ebp) 30: c7 45 d3 62 45 4a 78 movl $0x784a4562,-0x2d(%ebp) 37: c7 45 d7 4d 5a 52 4c movl $0x4c525a4d,-0x29(%ebp) 3e: c7 45 db 74 79 4f 4c movl $0x4c4f7974,-0x25(%ebp) 45: c7 45 df 61 57 6f 20 movl $0x206f5761,-0x21(%ebp) 4c: c7 45 e3 73 72 35 68 movl $0x68357273,-0x1d(%ebp) 53: c7 45 e7 20 7a 65 46 movl $0x46657a20,-0x19(%ebp) 5a: c7 45 eb 54 50 37 54 movl $0x54375054,-0x15(%ebp) 61: c7 45 ef 09 5a 73 4c movl $0x4c735a09,-0x11(%ebp) 68: c6 45 f3 00 movb $0x0,-0xd(%ebp) 6c: 83 ec 0c sub $0xc,%esp 6f: 8d 45 bb lea -0x45(%ebp),%eax 72: 50 push %eax 73: e8 fc ff ff ff call 74 <nndZqWCYPw+0x74> 78: 83 c4 10 add $0x10,%esp 7b: 89 45 f4 mov %eax,-0xc(%ebp) 7e: 83 7d 08 00 cmpl $0x0,0x8(%ebp) 82: 78 15 js 99 <nndZqWCYPw+0x99> 84: 8b 45 08 mov 0x8(%ebp),%eax 87: 3b 45 f4 cmp -0xc(%ebp),%eax 8a: 7d 0d jge 99 <nndZqWCYPw+0x99> 8c: 8d 55 bb lea -0x45(%ebp),%edx 8f: 8b 45 08 mov 0x8(%ebp),%eax 92: 01 d0 add %edx,%eax 94: 0f b6 00 movzbl (%eax),%eax 97: eb 05 jmp 9e <nndZqWCYPw+0x9e> 99: b8 00 00 00 00 mov $0x0,%eax 9e: c9 leave 9f: c3 ret
000000a0 <AFPQyOcF>: a0: 55 push %ebp a1: 89 e5 mov %esp,%ebp a3: 83 ec 08 sub $0x8,%esp a6: 83 ec 08 sub $0x8,%esp a9: 68 02 00 00 00 push $0x2 ae: ff 75 08 push 0x8(%ebp) b1: e8 fc ff ff ff call b2 <AFPQyOcF+0x12> b6: 83 c4 10 add $0x10,%esp b9: 85 c0 test %eax,%eax bb: 75 10 jne cd <AFPQyOcF+0x2d> bd: 83 ec 0c sub $0xc,%esp c0: ff 75 0c push 0xc(%ebp) c3: e8 fc ff ff ff call c4 <AFPQyOcF+0x24> c8: 83 c4 10 add $0x10,%esp cb: eb 01 jmp ce <AFPQyOcF+0x2e> cd: 90 nop ce: c9 leave cf: c3 ret
000000d0 <do_phase>: d0: 55 push %ebp d1: 89 e5 mov %esp,%ebp d3: 90 nop d4: 90 nop d5: 90 nop d6: 90 nop d7: 90 nop d8: 90 nop d9: 90 nop da: 90 nop db: 90 nop dc: 90 nop dd: 90 nop de: 90 nop df: 90 nop e0: 90 nop e1: 90 nop e2: 90 nop e3: 90 nop e4: 90 nop e5: 90 nop e6: 90 nop e7: 90 nop e8: 90 nop e9: 90 nop ea: 90 nop eb: 90 nop ec: 90 nop ed: 90 nop ee: 90 nop ef: 90 nop f0: 90 nop f1: 90 nop f2: 90 nop f3: 90 nop f4: 90 nop f5: 90 nop f6: 90 nop f7: 90 nop f8: 90 nop f9: 90 nop fa: 90 nop fb: 90 nop fc: 90 nop fd: 90 nop fe: 90 nop ff: 90 nop 100: 90 nop 101: 90 nop 102: 90 nop 103: 90 nop 104: 90 nop 105: 90 nop 106: 90 nop 107: 90 nop 108: 90 nop 109: 90 nop 10a: 90 nop 10b: 90 nop 10c: 90 nop 10d: 90 nop 10e: 90 nop 10f: 90 nop 110: 90 nop 111: 90 nop 112: 90 nop 113: 90 nop 114: 5d pop %ebp 115: c3 ret
我们需要在 do_phase 中填充一些指令,使其调用 AFPQyOcF 函数
nndZqWCYPw 函数与本阶段无关
通过对照 .rel.text 或反汇编可执行文件,可知 AFPQyOcF 函数的行为如下:
void AFPQyOcF(const char* first, const char* second) { if (strcmp(first, "yKSPHJa") == 0) { puts(second); }}
其中字符串 yKSPHJa
通过下面三条指令可以推断出来:
a9: 68 02 00 00 00 push $0x2 ae: ff 75 08 push 0x8(%ebp) b1: e8 fc ff ff ff call b2 <AFPQyOcF+0x12>
同样是对照 .rel.text 或反汇编可执行文件,可知这里 call 的是 strcmp,第一个参数为调用 AFPQyOcF 的第一个参数,第二个参数对照 .rel.text 可知在 .rodata 中,偏移为 0x2,我们查看 .rodata 的开头:
3200 794b 5350 484a 6100 0047
可知为 79 4b 53 50 48 4a 61 00
,即 yKSPHJa
或者通过 gdbgui 直接调试可执行文件也可知字符串地址在 0x804a0e6
处,为 yKSPHJa
同样可以分析出打印的字符串为调用 AFPQyOcF 的第二个参数
c0: ff 75 0c push 0xc(%ebp) c3: e8 fc ff ff ff call c4 <AFPQyOcF+0x24>
我们来复习一下 IA-32 的过程调用:
![e30ef9b1f3ef4fa59557b906d6b8b30e.png](https://vgalaxy-blog.oss-cn-nanjing.aliyuncs.com/assets/e30ef9b1f3ef4fa59557b906d6b8b30e.png)
在被调用过程中,调用过程的第一个参数在 0x8(%ebp),第二个参数在 0xc(%ebp) 以此类推
为此我们需要构造如下的函数调用:
void do_phase() { AFPQyOcF("yKSPHJa", "0809NJU064")}
也就需要构造 do_phase 的栈帧,如图所示:
![b81cb38be9464845aa0d65f703269217.png](https://vgalaxy-blog.oss-cn-nanjing.aliyuncs.com/assets/b81cb38be9464845aa0d65f703269217.png)
我们编写汇编代码:
do_phase: push %ebp movl %esp, %ebp subl $0x1c, %esp movl $0x00003436, -4(%ebp) movl $0x30554a4e, -8(%ebp) movl $0x39303830, -12(%ebp) movl $0x00614a48, -16(%ebp) movl $0x50534b79, -20(%ebp) leal -20(%ebp), %eax movl %eax, (%esp) leal -12(%ebp), %eax movl %eax, 4(%esp) call AFPQyOcF addl $0x1c, %esp
注意构造参数时为 leal 而非 movl,因为是地址
通过 gcc -m32 -c temp.S 可得:
Disassembly of section .text:
00000000 <do_phase>: 0: 55 push %ebp 1: 89 e5 mov %esp,%ebp 3: 83 ec 1c sub $0x1c,%esp 6: c7 45 fc 36 34 00 00 movl $0x3436,-0x4(%ebp) d: c7 45 f8 4e 4a 55 30 movl $0x30554a4e,-0x8(%ebp) 14: c7 45 f4 30 38 30 39 movl $0x39303830,-0xc(%ebp) 1b: c7 45 f0 48 4a 61 00 movl $0x614a48,-0x10(%ebp) 22: c7 45 ec 79 4b 53 50 movl $0x50534b79,-0x14(%ebp) 29: 8d 45 ec lea -0x14(%ebp),%eax 2c: 89 04 24 mov %eax,(%esp) 2f: 8d 45 f4 lea -0xc(%ebp),%eax 32: 89 44 24 04 mov %eax,0x4(%esp) 36: e8 fc ff ff ff call 37 <do_phase+0x37> 3b: 83 c4 1c add $0x1c,%esp
注意到偏移为 -(0xd0 - 0xa0 + 3b) = 0xffffff95
,对应修改 phase.o 即可
最终 phase.o 的 do_phase 反汇编如下:
000000d0 <do_phase>: d0: 55 push %ebp d1: 89 e5 mov %esp,%ebp d3: 83 ec 1c sub $0x1c,%esp d6: c7 45 fc 36 34 00 00 movl $0x3436,-0x4(%ebp) dd: c7 45 f8 4e 4a 55 30 movl $0x30554a4e,-0x8(%ebp) e4: c7 45 f4 30 38 30 39 movl $0x39303830,-0xc(%ebp) eb: c7 45 f0 48 4a 61 00 movl $0x614a48,-0x10(%ebp) f2: c7 45 ec 79 4b 53 50 movl $0x50534b79,-0x14(%ebp) f9: 8d 45 ec lea -0x14(%ebp),%eax fc: 89 04 24 mov %eax,(%esp) ff: 8d 45 f4 lea -0xc(%ebp),%eax 102: 89 44 24 04 mov %eax,0x4(%esp) 106: e8 95 ff ff ff call a0 <AFPQyOcF> 10b: 83 c4 1c add $0x1c,%esp 10e: 90 nop 10f: 90 nop 110: 90 nop 111: 90 nop 112: 90 nop 113: 90 nop 114: 5d pop %ebp 115: c3 ret
phase3 - switch 语句与重定位
不允许修改 .text section 和 relocation section 的内容
readelf
Relocation section
Relocation section '.rel.text' at offset 0x4a4 contains 2 entries: Offset Info Type Sym.Value Sym. Name00000075 00000701 R_386_32 00000000 .rodata00000153 00000d02 R_386_PC32 00000000 puts
Relocation section '.rel.data' at offset 0x4b4 contains 2 entries: Offset Info Type Sym.Value Sym. Name000000f4 00000701 R_386_32 00000000 .rodata000000f8 00000c01 R_386_32 0000002a do_phase
Relocation section '.rel.rodata' at offset 0x4c4 contains 26 entries: Offset Info Type Sym.Value Sym. Name00000004 00000201 R_386_32 00000000 .text00000008 00000201 R_386_32 00000000 .text0000000c 00000201 R_386_32 00000000 .text00000010 00000201 R_386_32 00000000 .text00000014 00000201 R_386_32 00000000 .text00000018 00000201 R_386_32 00000000 .text0000001c 00000201 R_386_32 00000000 .text00000020 00000201 R_386_32 00000000 .text00000024 00000201 R_386_32 00000000 .text00000028 00000201 R_386_32 00000000 .text0000002c 00000201 R_386_32 00000000 .text00000030 00000201 R_386_32 00000000 .text00000034 00000201 R_386_32 00000000 .text00000038 00000201 R_386_32 00000000 .text0000003c 00000201 R_386_32 00000000 .text00000040 00000201 R_386_32 00000000 .text00000044 00000201 R_386_32 00000000 .text00000048 00000201 R_386_32 00000000 .text0000004c 00000201 R_386_32 00000000 .text00000050 00000201 R_386_32 00000000 .text00000054 00000201 R_386_32 00000000 .text00000058 00000201 R_386_32 00000000 .text0000005c 00000201 R_386_32 00000000 .text00000060 00000201 R_386_32 00000000 .text00000064 00000201 R_386_32 00000000 .text00000068 00000201 R_386_32 00000000 .text
objdump
0000002a <do_phase>: 2a: 55 push %ebp 2b: 89 e5 mov %esp,%ebp 2d: 83 ec 28 sub $0x28,%esp 30: c7 45 e5 54 50 44 46 movl $0x46445054,-0x1b(%ebp) 37: c7 45 e9 4f 43 59 41 movl $0x4159434f,-0x17(%ebp) 3e: 66 c7 45 ed 5a 53 movw $0x535a,-0x13(%ebp) 44: c6 45 ef 00 movb $0x0,-0x11(%ebp) 48: c7 45 f0 00 00 00 00 movl $0x0,-0x10(%ebp) 4f: e9 e0 00 00 00 jmp 134 <do_phase+0x10a> 54: 8d 55 e5 lea -0x1b(%ebp),%edx 57: 8b 45 f0 mov -0x10(%ebp),%eax 5a: 01 d0 add %edx,%eax 5c: 0f b6 00 movzbl (%eax),%eax 5f: 88 45 f7 mov %al,-0x9(%ebp) 62: 0f be 45 f7 movsbl -0x9(%ebp),%eax 66: 83 e8 41 sub $0x41,%eax 69: 83 f8 19 cmp $0x19,%eax 6c: 0f 87 b0 00 00 00 ja 122 <do_phase+0xf8> 72: 8b 04 85 04 00 00 00 mov 0x4(,%eax,4),%eax 79: ff e0 jmp *%eax 7b: c6 45 f7 36 movb $0x36,-0x9(%ebp) 7f: e9 9e 00 00 00 jmp 122 <do_phase+0xf8> 84: c6 45 f7 22 movb $0x22,-0x9(%ebp) 88: e9 95 00 00 00 jmp 122 <do_phase+0xf8> 8d: c6 45 f7 29 movb $0x29,-0x9(%ebp) 91: e9 8c 00 00 00 jmp 122 <do_phase+0xf8> 96: c6 45 f7 30 movb $0x30,-0x9(%ebp) 9a: e9 83 00 00 00 jmp 122 <do_phase+0xf8> 9f: c6 45 f7 23 movb $0x23,-0x9(%ebp) a3: eb 7d jmp 122 <do_phase+0xf8> a5: c6 45 f7 38 movb $0x38,-0x9(%ebp) a9: eb 77 jmp 122 <do_phase+0xf8> ab: c6 45 f7 64 movb $0x64,-0x9(%ebp) af: eb 71 jmp 122 <do_phase+0xf8> b1: c6 45 f7 5a movb $0x5a,-0x9(%ebp) b5: eb 6b jmp 122 <do_phase+0xf8> b7: c6 45 f7 4a movb $0x4a,-0x9(%ebp) bb: eb 65 jmp 122 <do_phase+0xf8> bd: c6 45 f7 38 movb $0x38,-0x9(%ebp) c1: eb 5f jmp 122 <do_phase+0xf8> c3: c6 45 f7 4e movb $0x4e,-0x9(%ebp) c7: eb 59 jmp 122 <do_phase+0xf8> c9: c6 45 f7 34 movb $0x34,-0x9(%ebp) cd: eb 53 jmp 122 <do_phase+0xf8> cf: c6 45 f7 69 movb $0x69,-0x9(%ebp) d3: eb 4d jmp 122 <do_phase+0xf8> d5: c6 45 f7 72 movb $0x72,-0x9(%ebp) d9: eb 47 jmp 122 <do_phase+0xf8> db: c6 45 f7 77 movb $0x77,-0x9(%ebp) df: eb 41 jmp 122 <do_phase+0xf8> e1: c6 45 f7 37 movb $0x37,-0x9(%ebp) e5: eb 3b jmp 122 <do_phase+0xf8> e7: c6 45 f7 2d movb $0x2d,-0x9(%ebp) eb: eb 35 jmp 122 <do_phase+0xf8> ed: c6 45 f7 61 movb $0x61,-0x9(%ebp) f1: eb 2f jmp 122 <do_phase+0xf8> f3: c6 45 f7 38 movb $0x38,-0x9(%ebp) f7: eb 29 jmp 122 <do_phase+0xf8> f9: c6 45 f7 71 movb $0x71,-0x9(%ebp) fd: eb 23 jmp 122 <do_phase+0xf8> ff: c6 45 f7 39 movb $0x39,-0x9(%ebp) 103: eb 1d jmp 122 <do_phase+0xf8> 105: c6 45 f7 50 movb $0x50,-0x9(%ebp) 109: eb 17 jmp 122 <do_phase+0xf8> 10b: c6 45 f7 67 movb $0x67,-0x9(%ebp) 10f: eb 11 jmp 122 <do_phase+0xf8> 111: c6 45 f7 55 movb $0x55,-0x9(%ebp) 115: eb 0b jmp 122 <do_phase+0xf8> 117: c6 45 f7 68 movb $0x68,-0x9(%ebp) 11b: eb 05 jmp 122 <do_phase+0xf8> 11d: c6 45 f7 63 movb $0x63,-0x9(%ebp) 121: 90 nop 122: 8d 55 da lea -0x26(%ebp),%edx 125: 8b 45 f0 mov -0x10(%ebp),%eax 128: 01 c2 add %eax,%edx 12a: 0f b6 45 f7 movzbl -0x9(%ebp),%eax 12e: 88 02 mov %al,(%edx) 130: 83 45 f0 01 addl $0x1,-0x10(%ebp) 134: 8b 45 f0 mov -0x10(%ebp),%eax 137: 83 f8 09 cmp $0x9,%eax 13a: 0f 86 14 ff ff ff jbe 54 <do_phase+0x2a> 140: 8d 55 da lea -0x26(%ebp),%edx 143: 8b 45 f0 mov -0x10(%ebp),%eax 146: 01 d0 add %edx,%eax 148: c6 00 00 movb $0x0,(%eax) 14b: 83 ec 0c sub $0xc,%esp 14e: 8d 45 da lea -0x26(%ebp),%eax 151: 50 push %eax 152: e8 fc ff ff ff call 153 <do_phase+0x129> 157: 83 c4 10 add $0x10,%esp 15a: 90 nop 15b: c9 leave 15c: c3 ret
call 的函数为 puts
经过调试可知 COOKIE 字符串为 TPDFOCYAZS,进行的变换如下
对目标字符串下标为 i 的字符,在下面的地址处
会有一个地址,该地址处会有一条 movb 语句,其操作数即为该字符
注意到 0x41 即为 A,为此,我们需要修改跳转表
vgalaxy@vgalaxy-VirtualBox:~/Lab/linklab$ hexdump -s 0x29c -n 0x6c phase3.o000029c 0033 0000 00b7 0000 00c9 0000 00db 000000002ac 00ff 0000 00c3 0000 00d5 0000 008d 000000002bc 00f9 0000 009f 0000 007b 0000 0117 000000002cc 0084 0000 011d 0000 00e7 0000 00ed 000000002dc 0096 0000 00e1 0000 00a5 0000 00b1 000000002ec 00bd 0000 0111 0000 00f3 0000 00ab 000000002fc 010b 0000 0105 0000 00cf 00000000308
注意到 .rel.rodata 的存在,且从第 1 个表项开始(从 0 计数),反映了这种间接寻址
调试可知第 1 个表项 b7 对应实际地址 0x804926d,即 movb $0x4a,-0x9(%ebp)
发现 b7 就是在 .text 中的偏移
找到一个对应关系,我们就能推导出所有的映射
cookie | offset | item | addr | string |
---|---|---|---|---|
T | 19 | bd → 96 | 30 | 0 |
P | 15 | 96 → bd | 38 | 8 |
D | 3 | ff → 96 | 30 | 0 |
F | 5 | d5 → ff | 39 | 9 |
O | 14 | ed → c3 | 4e | N |
C | 2 | db → b7 | 4a | J |
Y | 24 | 105 → 111 | 55 | U |
A | 0 | b7 → 96 | 30 | 0 |
Z | 25 | cf → 7b | 36 | 6 |
S | 18 | b1 → c9 | 34 | 4 |
参考 1
vgalaxy@vgalaxy-VirtualBox:~/Lab/linklab$ hexdump -s 0x2a0 -n 0x6c phase3.o00002a0 00b7 0000 00c9 0000 00db 0000 00ff 000000002b0 00c3 0000 00d5 0000 008d 0000 00f9 000000002c0 009f 0000 007b 0000 0117 0000 0084 000000002d0 011d 0000 00e7 0000 00ed 0000 0096 000000002e0 00e1 0000 00a5 0000 00b1 0000 00bd 000000002f0 0111 0000 00f3 0000 00ab 0000 010b 00000000300 0105 0000 00cf 0000 4700 4343000030c
参考 2
7b: c6 45 f7 36 movb $0x36,-0x9(%ebp) 84: c6 45 f7 22 movb $0x22,-0x9(%ebp) 8d: c6 45 f7 29 movb $0x29,-0x9(%ebp) 96: c6 45 f7 30 movb $0x30,-0x9(%ebp) 9f: c6 45 f7 23 movb $0x23,-0x9(%ebp) a5: c6 45 f7 38 movb $0x38,-0x9(%ebp) ab: c6 45 f7 64 movb $0x64,-0x9(%ebp) b1: c6 45 f7 5a movb $0x5a,-0x9(%ebp) b7: c6 45 f7 4a movb $0x4a,-0x9(%ebp) bd: c6 45 f7 38 movb $0x38,-0x9(%ebp) c3: c6 45 f7 4e movb $0x4e,-0x9(%ebp) c9: c6 45 f7 34 movb $0x34,-0x9(%ebp) cf: c6 45 f7 69 movb $0x69,-0x9(%ebp) d5: c6 45 f7 72 movb $0x72,-0x9(%ebp) db: c6 45 f7 77 movb $0x77,-0x9(%ebp) e1: c6 45 f7 37 movb $0x37,-0x9(%ebp) e7: c6 45 f7 2d movb $0x2d,-0x9(%ebp) ed: c6 45 f7 61 movb $0x61,-0x9(%ebp) f3: c6 45 f7 38 movb $0x38,-0x9(%ebp) f9: c6 45 f7 71 movb $0x71,-0x9(%ebp) ff: c6 45 f7 39 movb $0x39,-0x9(%ebp) 105: c6 45 f7 50 movb $0x50,-0x9(%ebp) 10b: c6 45 f7 67 movb $0x67,-0x9(%ebp) 111: c6 45 f7 55 movb $0x55,-0x9(%ebp) 117: c6 45 f7 68 movb $0x68,-0x9(%ebp) 11d: c6 45 f7 63 movb $0x63,-0x9(%ebp)
对应修改即可
phase4 - 可重定位目标文件
修改 relocation section 的内容
readelf
Section Headers
Section Headers: [Nr] Name Type Addr Off Size ES Flg Lk Inf Al [ 0] NULL 00000000 000000 000000 00 0 0 0 [ 1] .text PROGBITS 00000000 000034 00027c 00 AX 0 0 1 [ 2] .rel.text REL 00000000 000738 0000b8 08 I 12 1 4 [ 3] .data PROGBITS 00000000 0002c0 000048 00 WA 0 0 32 [ 4] .rel.data REL 00000000 0007f0 000020 08 I 12 3 4 [ 5] .bss NOBITS 00000000 000308 000000 00 WA 0 0 1 [ 6] .rodata PROGBITS 00000000 000320 000100 00 A 0 0 32 [ 7] .rel.rodata REL 00000000 000810 000040 08 I 12 6 4 [ 8] .comment PROGBITS 00000000 000420 00001d 01 MS 0 0 1 [ 9] .note.GNU-stack PROGBITS 00000000 00043d 000000 00 0 0 1 [10] .eh_frame PROGBITS 00000000 000440 0000d8 00 A 0 0 4 [11] .rel.eh_frame REL 00000000 000850 000030 08 I 12 10 4 [12] .symtab SYMTAB 00000000 000518 000190 10 13 9 4 [13] .strtab STRTAB 00000000 0006a8 00008f 00 0 0 1 [14] .shstrtab STRTAB 00000000 000880 000067 00 0 0 1
Relocation section
Relocation section '.rel.text' at offset 0x738 contains 23 entries: Offset Info Type Sym.Value Sym. Name00000000 00000000 R_386_NONE0000007f 00000501 R_386_32 00000000 .rodata00000000 00000000 R_386_NONE00000000 00000000 R_386_NONE000000b5 00000d01 R_386_32 00000020 CMKbeL000000c7 00000d01 R_386_32 00000020 CMKbeL000000d6 00000d01 R_386_32 00000020 CMKbeL000000e7 00000d01 R_386_32 00000020 CMKbeL00000103 00000e01 R_386_32 00000038 vvWaVk00000000 00000000 R_386_NONE00000000 00000000 R_386_NONE00000122 00000e01 R_386_32 00000038 vvWaVk00000142 00001302 R_386_PC32 00000000 strlen00000166 00001101 R_386_32 00000080 KvXOBb0000016c 00000e01 R_386_32 00000038 vvWaVk000001ca 00001302 R_386_PC32 00000000 strlen000001ee 00001101 R_386_32 00000080 KvXOBb000001f4 00000e01 R_386_32 00000038 vvWaVk00000000 00000000 R_386_NONE00000258 00001501 R_386_32 0000003c encoder00000260 00000c01 R_386_32 0000002c OdZAJybs0000026d 00000c01 R_386_32 0000002c OdZAJybs00000272 00001702 R_386_PC32 00000000 puts
Relocation section '.rel.data' at offset 0x7f0 contains 4 entries: Offset Info Type Sym.Value Sym. Name00000028 00000501 R_386_32 00000000 .rodata00000000 00000000 R_386_NONE00000040 00001401 R_386_32 000001bd encode_200000044 00001601 R_386_32 00000244 do_phase
Relocation section '.rel.rodata' at offset 0x810 contains 8 entries: Offset Info Type Sym.Value Sym. Name00000060 00000201 R_386_32 00000000 .text00000064 00000201 R_386_32 00000000 .text00000068 00000201 R_386_32 00000000 .text0000006c 00000201 R_386_32 00000000 .text00000070 00000201 R_386_32 00000000 .text00000074 00000201 R_386_32 00000000 .text00000078 00000201 R_386_32 00000000 .text0000007c 00000201 R_386_32 00000000 .text
代码框架
/* NOTE: Those capitalized variable names in following code will be substituted by different actual names in the module. */
char BUFFER[] = ......;const int CODE_TRAN_ARRAY[] = ......;int CODE = ......;const char DICT[] = ......;...... // Definitions of other variables
int transform_code( int code, int mode ) { switch ( CODE_TRAN_ARRAY[mode] ... ) { case 0: ...... case 1: ...... ...... default: ...... } return code;}
void generate_code( int cookie ) { ... = cookie; for ( i = 0; i < ...; i++ ) { ... = transform_code( ..., i ); }}
int encode_1( char* str ) { ...... for (i = 0; i < n; i++) { str[i] = DICT[str[i]] ...; if (str[i] < 0x20 || str[i] > 0x7E) str[i] = ...; } ......}
int encode_2( char* str ) { ...... // Similar to encode_1 ......}
typedef int (*CODER)(char*);CODER encoder[] = { ...... };
void do_phase() { generate_code(...); ......; // Call one encoder here printf("%s\n", ...);}......
.rel.text 缺失 6 个,.rel.data 缺失 1 个
CMKbeL 对应 CODE_TRAN_ARRAY
6d: 8b 04 85 00 00 00 00 mov 0x0(,%eax,4),%eax 8d: 8b 04 85 00 00 00 00 mov 0x0(,%eax,4),%eax a1: 8b 04 85 00 00 00 00 mov 0x0(,%eax,4),%eax b2: 8b 04 85 00 00 00 00 mov 0x0(,%eax,4),%eax c4: 8b 04 85 00 00 00 00 mov 0x0(,%eax,4),%eax d3: 8b 04 85 00 00 00 00 mov 0x0(,%eax,4),%eax e4: 8b 04 85 00 00 00 00 mov 0x0(,%eax,4),%eax
未缺失
000000b5 00000d01 R_386_32 00000020 CMKbeL000000c7 00000d01 R_386_32 00000020 CMKbeL000000d6 00000d01 R_386_32 00000020 CMKbeL000000e7 00000d01 R_386_32 00000020 CMKbeL
缺失 70 / 90 / a4
vvWaVk 对应 CODE
00000103 00000e01 R_386_32 00000038 vvWaVk00000122 00000e01 R_386_32 00000038 vvWaVk0000016c 00000e01 R_386_32 00000038 vvWaVk000001f4 00000e01 R_386_32 00000038 vvWaVk
未缺失
000000f9 <generate_code>: 102: a3 00 00 00 00 mov %eax,0x0 121: a3 00 00 00 00 mov %eax,0x0
00000135 <encode_1>: 16a: 8b 15 00 00 00 00 mov 0x0,%edx
000001bd <encode_2>: 1f2: 8b 15 00 00 00 00 mov 0x0,%edx
KvXOBb 对应 DICT
00000166 00001101 R_386_32 00000080 KvXOBb000001ee 00001101 R_386_32 00000080 KvXOBb
未缺失
00000135 <encode_1>: 163: 0f b6 80 00 00 00 00 movzbl 0x0(%eax),%eax
000001bd <encode_2>: 1eb: 0f b6 80 00 00 00 00 movzbl 0x0(%eax),%eax
OdZAJybs 对应 BUFFER
00000260 00000c01 R_386_32 0000002c OdZAJybs0000026d 00000c01 R_386_32 0000002c OdZAJybs
未缺失
00000244 <do_phase>: 25f: 68 00 00 00 00 push $0x0 26c: 68 00 00 00 00 push $0x0
puts
00000272 00001702 R_386_PC32 00000000 puts
对应
00000244 <do_phase>: 271: e8 fc ff ff ff call 272 <do_phase+0x2e>
encoder
00000258 00001501 R_386_32 0000003c encoder
对应
00000244 <do_phase>: 257: a1 00 00 00 00 mov 0x0,%eax
strlen
00000142 00001302 R_386_PC32 00000000 strlen000001ca 00001302 R_386_PC32 00000000 strlen
对应
00000135 <encode_1>: 141: e8 fc ff ff ff call 142 <encode_1+0xd>
000001bd <encode_2>: 1c9: e8 fc ff ff ff call 1ca <encode_2+0xd>
注意下面两个没有出现在 relocation section 中,可以通过范围来判断:
00000135 <encode_1>: 14c: c7 45 f4 00 00 00 00 movl $0x0,-0xc(%ebp)
000001bd <encode_2>: 1d4: c7 45 f4 00 00 00 00 movl $0x0,-0xc(%ebp)
还有
000000f9 <generate_code>: 107: c7 45 fc 00 00 00 00 movl $0x0,-0x4(%ebp)
这是 for 循环初始化循环变量
不要以为操作数是
00 00 00 00
就需要重定位
综上,.rel.text 剩下的缺失如下:
000000f9 <generate_code>: 110: a1 00 00 00 00 mov 0x0,%eax 119: e8 fc ff ff ff call 11a <generate_code+0x21>
00000244 <do_phase>: 24f: e8 fc ff ff ff call 250 <do_phase+0xc>
这里应该对应 CODE,即 vvWaVk,为调用 transform_code 准备第一个参数
110: a1 00 00 00 00 mov 0x0,%eax
这里则是调用 transform_code
119: e8 fc ff ff ff call 11a <generate_code+0x21>
这里则是调用 generate_code
24f: e8 fc ff ff ff call 250 <do_phase+0xc>
分析完 .rel.text 后,我们研究一下重定位表项的数据结构
typedef struct{ Elf32_Addr r_offset; /* Address */ Elf32_Word r_info; /* Relocation type and symbol index */} Elf32_Rel;
#define ELF32_R_SYM(val) ((val) >> 8)#define ELF32_R_TYPE(val) ((val) & 0xff)#define ELF32_R_INFO(sym, type) (((sym) << 8) + ((type) & 0xff))
/usr/include/elf.h
定位 .rel.text 的二进制表示
vgalaxy@vgalaxy-VirtualBox:~/Lab/linklab$ hexdump -s 0x738 -n 0xb8 phase4.o0000738 0000 0000 0000 0000 007f 0000 0501 00000000748 0000 0000 0000 0000 0000 0000 0000 00000000758 00b5 0000 0d01 0000 00c7 0000 0d01 00000000768 00d6 0000 0d01 0000 00e7 0000 0d01 00000000778 0103 0000 0e01 0000 0000 0000 0000 00000000788 0000 0000 0000 0000 0122 0000 0e01 00000000798 0142 0000 1302 0000 0166 0000 1101 000000007a8 016c 0000 0e01 0000 01ca 0000 1302 000000007b8 01ee 0000 1101 0000 01f4 0000 0e01 000000007c8 0000 0000 0000 0000 0258 0000 1501 000000007d8 0260 0000 0c01 0000 026d 0000 0c01 000000007e8 0272 0000 1702 000000007f0
先补充前三个缺失 70 / 90 / a4
00000070 00000d01 R_386_32 00000020 CMKbeL00000090 00000d01 R_386_32 00000020 CMKbeL000000a4 00000d01 R_386_32 00000020 CMKbeL000000b5 00000d01 R_386_32 00000020 CMKbeL000000c7 00000d01 R_386_32 00000020 CMKbeL000000d6 00000d01 R_386_32 00000020 CMKbeL000000e7 00000d01 R_386_32 00000020 CMKbeL
第四个
00000111 00000e01 R_386_32 00000038 vvWaVk
下面两个是 PC 相对寻址,r_info 部分高 24 位是符号索引,低 8 位是重定位类型
看一看符号表
Symbol table '.symtab' contains 25 entries: Num: Value Size Type Bind Vis Ndx Name 0: 00000000 0 NOTYPE LOCAL DEFAULT UND 1: 00000000 0 FILE LOCAL DEFAULT ABS phase4.c 2: 00000000 0 SECTION LOCAL DEFAULT 1 3: 00000000 0 SECTION LOCAL DEFAULT 3 4: 00000000 0 SECTION LOCAL DEFAULT 5 5: 00000000 0 SECTION LOCAL DEFAULT 6 6: 00000000 0 SECTION LOCAL DEFAULT 9 7: 00000000 0 SECTION LOCAL DEFAULT 10 8: 00000000 0 SECTION LOCAL DEFAULT 8 9: 00000000 38 OBJECT GLOBAL DEFAULT 3 BvuGmt 10: 00000000 103 FUNC GLOBAL DEFAULT 1 nndZqWCYPw 11: 00000028 4 OBJECT GLOBAL DEFAULT 3 phase_id 12: 0000002c 11 OBJECT GLOBAL DEFAULT 3 OdZAJybs 13: 00000020 64 OBJECT GLOBAL DEFAULT 6 CMKbeL 14: 00000038 4 OBJECT GLOBAL DEFAULT 3 vvWaVk 15: 00000067 146 FUNC GLOBAL DEFAULT 1 transform_code 16: 000000f9 60 FUNC GLOBAL DEFAULT 1 generate_code 17: 00000080 128 OBJECT GLOBAL DEFAULT 6 KvXOBb 18: 00000135 136 FUNC GLOBAL DEFAULT 1 encode_1 19: 00000000 0 NOTYPE GLOBAL DEFAULT UND strlen 20: 000001bd 135 FUNC GLOBAL DEFAULT 1 encode_2 21: 0000003c 8 OBJECT GLOBAL DEFAULT 3 encoder 22: 00000244 56 FUNC GLOBAL DEFAULT 1 do_phase 23: 00000000 0 NOTYPE GLOBAL DEFAULT UND puts 24: 00000044 4 OBJECT GLOBAL DEFAULT 3 phase
举个例子:
00000142 00001302 R_386_PC32 00000000 strlen
0x13 → 19 → strlen
所以第五个为 11a 0f02,第六个为 250 1002
0000011a 00000f02 R_386_PC32 00000067 transform_code00000250 00001002 R_386_PC32 000000f9 generate_code
最后一个在 .rel.data
Relocation section '.rel.data' at offset 0x7f0 contains 4 entries: Offset Info Type Sym.Value Sym. Name00000028 00000501 R_386_32 00000000 .rodata00000000 00000000 R_386_NONE00000040 00001401 R_386_32 000001bd encode_200000044 00001601 R_386_32 00000244 do_phase
看一下 .data
vgalaxy@vgalaxy-VirtualBox:~/Lab/linklab$ hexdump -s 0x2c0 -n 0x48 phase4.o00002c0 acd0 3cd3 36b1 659e e49b 4e58 fe3d d31a00002d0 47a0 c1b4 a3b9 e15a eb1d c783 6cf0 26a200002e0 1d2a 8b39 04ec 0000 0000 0000 3830 393000002f0 4a4e 3055 3436 0000 ffff ffff 0000 00000000300 0000 0000 0000 00000000308
猜测在偏移 0x3c 处为 encode_1,即 3c 1201
0000003c 00001201 R_386_32 00000135 encode_1
但是最后的输出似乎和实验指南中不一致:
vgalaxy@vgalaxy-VirtualBox:~/Lab/linklab$ make phase4gcc -m32 -no-pie -o linkbomb main.o phase4.o./linkbombUWU??$]UA8
算了,不想再看了……