起因如上……
額,先把平臺放一下,因爲有些代碼設計系統架構,如果你是x86 的架構需要自己修改代碼:
首先是平時調用glibc 的C 程序:
#include <stdio.h>
int
main (void) {
printf ("Hello World!\n");
return 0;
}
看一下大小,哇,足足有將近7KB:階段1:在平時的基礎上使用strip
恩不錯,還剩4K 多一點:
階段2:不使用glibc 並且strip
哇!只剩下520B 了有木有!直接調用系統調用竟然把可執行文件的體積縮小了這麼多!
.section .data
aStr: .ascii "Hello World!\n"
aStrEnd:
.section .text
.global _start
_start:
movq $1, %rdi
movq $aStr, %rsi
movq $(aStrEnd-aStr), %rdx
movq $1, %rax
syscall
movq $0, %rdi
movq $60, %rax
syscall
階段3:克勤克儉用指令體積
我們應該儘量減少指令編譯後形成機器碼的體積,儘量使之最小!
哇!通過精心的挑選指令,ELF 文件體積減小到了496 B:
.section .data
aStr: .ascii "Hello World!\n"
aStrEnd:
.section .text
.global _start
_start:
movw $1, %di
movl $aStr, %esi
movb $(aStrEnd-aStr), %dl
movb $1, %al
syscall
xor %di, %di
movb $60, %al
syscall
階段4:不再使用段
就是這樣,喵,當然strip 還是要的,看看怎麼樣,哇,新的記錄368 字節:
aStr: .ascii "Hello World!\n"
aStrEnd:
.global _start
_start:
movw $1, %di
movl $aStr, %esi
movb $(aStrEnd-aStr), %dl
movb $1, %al
syscall
xor %di, %di
movb $60, %al
syscall
階段5:目標文件中“沒用”的東西統統扔掉!
上面分別使用syscall 代替了glibc,調整了指令的大小,並且去掉了分段,接下來在這個基礎上對ELF 下手吧!
先看看有用的東西(ELF 頭、程序頭和節頭)有多少,64+56+64 = 184B:
只留下這184B,剩下的統統不要了!
最後的到了什麼?瞧!一個不到200 字節的Hello World!讓我們掐去腦袋,它可以給你提供……