动态调试elf文件的几种方法
0x01 ida动态调试
0x02 gdb动态调试
gdb <program> //启动
quit //结束
run:简写为r,运行调试程序,直到断点处
stepi:简写为s,执行一条指令,步入函数
nexti:简写为n,执行一条指令,步过函数
continue:简写为c,继续执行
until:在一个循环体内部单步跟踪的时候,可以通过until命令跳出循环
until+行号:运行至某行
break *address:简写b *address,设置断点
info breakpoints:简写为info b,查看断点
delete *address:删除断点
disable *address:暂停断点
enable *address:开启断点
delete breakpoints:删除所有断点
info register:简写为info r,查看寄存器
x/countFormatSize addr:以指定格式Format打印地址address处的指定大小size、指定数量count的对象
Size:b(字节)、h(半字)、w(字)、g(8字节)
Format:o(八进制)、d(十进制)、x(十六进制)、u(无符号十进制)、t(二进制)、f(浮点数)、a(地 址)、i(指令)、c(字符)、s(字符串)
backtrace:打印函数调用栈回溯
set $reg=value:修改寄存器
set *(type*)(address)=value:修改内存地址addr为value
0x03 radare2动态调试
$ r2 ./e3dd9674429f4ce1a25c08ea799fc027
[0x00400660]> aaa
[x] Analyze all flags starting with sym. and entry0 (aa)
[x] Analyze function calls (aac)
[x] Analyze len bytes of instructions for references (aar)
[x] Check for vtables
[x] Type matching analysis for all functions (aaft)
[x] Propagate noreturn information
[x] Use -AA or aaaa to perform additional experimental analysis.
r2 -A ./program
来直接分析程序$ r2 -A ./e3dd9674429f4ce1a25c08ea799fc027
[x] Analyze all flags starting with sym. and entry0 (aa)
[x] Analyze function calls (aac)
[x] Analyze len bytes of instructions for references (aar)
[x] Check for vtables
[x] Type matching analysis for all functions (aaft)
[x] Propagate noreturn information
[x] Use -AA or aaaa to perform additional experimental analysis.
iI
命令可以提供很多有用的信息iI
arch x86
baddr 0x400000
binsz 9449
bintype elf
bits 64
canary true
class ELF64
compiler GCC: (Ubuntu 5.4.1-2ubuntu1~14.04) 5.4.1 20160904 GCC: (Ubuntu 4.8.4-2ubuntu1~14.04.3) 4.8.4
crypto false
endian little
havecode true
intrp /lib64/ld-linux-x86-64.so.2
laddr 0x0
lang c
linenum true
lsyms true
machine AMD x86-64 architecture
maxopsz 16
minopsz 1
nx true
os linux
pcalign 0
pic false
relocs true
relro partial
rpath NONE
sanitiz false
static false
stripped false
subsys linux
va true
ii
和iE
命令来看下程序的导入和导出函数,从而能够更好的了解程序实现的功能ii
[Imports]
nth vaddr bind type lib name
―――――――――――――――――――――――――――――――――――――
1 0x004005c0 GLOBAL FUNC remove
2 0x004005d0 GLOBAL FUNC fclose
3 0x004005e0 GLOBAL FUNC strlen
4 0x004005f0 GLOBAL FUNC __stack_chk_fail
5 0x00400600 GLOBAL FUNC fputc
6 0x00400610 GLOBAL FUNC __libc_start_main
7 0x00400620 GLOBAL FUNC fprintf
8 0x00400630 WEAK NOTYPE __gmon_start__
9 0x00400640 GLOBAL FUNC fseek
10 0x00400650 GLOBAL FUNC fopen
iE
[Exports]
nth paddr vaddr bind type size lib name
――――――――――――――――――――――――――――――――――――――――――――――――――――――
45 0x00000960 0x00400960 GLOBAL FUNC 2 __libc_csu_fini
49 0x000010e0 0x006010e0 GLOBAL OBJ 44 t
50 ---------- 0x0060120c GLOBAL NOTYPE 0 _edata
51 0x00001160 0x00601160 GLOBAL OBJ 172 p
53 0x00000964 0x00400964 GLOBAL FUNC 0 _fini
58 0x00001080 0x00601080 GLOBAL NOTYPE 0 __data_start
61 0x00001088 0x00601088 GLOBAL OBJ 0 __dso_handle
62 0x00000970 0x00400970 GLOBAL OBJ 4 _IO_stdin_used
63 0x000008f0 0x004008f0 GLOBAL FUNC 101 __libc_csu_init
64 ---------- 0x00601210 GLOBAL NOTYPE 0 _end
65 0x00000660 0x00400660 GLOBAL FUNC 0 _start
67 0x000010a0 0x006010a0 GLOBAL OBJ 33 s
68 0x00001120 0x00601120 GLOBAL OBJ 44 u
69 ---------- 0x0060120c GLOBAL NOTYPE 0 __bss_start
70 0x00000756 0x00400756 GLOBAL FUNC 407 main
73 ---------- 0x00601210 GLOBAL OBJ 0 __TMC_END__
75 0x00000590 0x00400590 GLOBAL FUNC 0 _init
afl
命令查看程序存在的函数,从而找到main函数,定位到对应的位置,查看反汇编代码[0x00400660]> afl
0x00400660 1 41 entry0
0x00400610 1 6 sym.imp.__libc_start_main
0x00400690 4 50 -> 41 sym.deregister_tm_clones
0x004006d0 4 58 -> 55 sym.register_tm_clones
0x00400710 3 28 sym.__do_global_dtors_aux
0x00400730 4 38 -> 35 entry.init0
0x00400960 1 2 sym.__libc_csu_fini
0x00400964 1 9 sym._fini
0x004008f0 4 101 sym.__libc_csu_init
0x00400756 12 407 main
0x00400590 3 26 sym._init
0x00400630 1 6 loc.imp.__gmon_start__
0x004005c0 1 6 sym.imp.remove
0x004005d0 1 6 sym.imp.fclose
0x004005e0 1 6 sym.imp.strlen
0x004005f0 1 6 sym.imp.__stack_chk_fail
0x00400600 1 6 sym.imp.fputc
0x00400620 1 6 sym.imp.fprintf
0x00400640 1 6 sym.imp.fseek
0x00400650 1 6 sym.imp.fopen
axt
命令来查看函数调用[0x00400660]> axt main
entry0 0x40067d [DATA] mov rdi, main
s
命令定位到main函数,pdf
命令来查看函数的反汇编代码,s
命令后可以加地址或者函数名[ ]> s main
; DATA XREF from entry0 @ 0x40067d
┌ 407: int main (int argc, char **argv, char **envp);
│ ; var int64_t var_40h @ rbp-0x40
│ ; var int64_t var_3ch @ rbp-0x3c
│ ; var file*stream @ rbp-0x38
│ ; var char *filename @ rbp-0x30
│ ; var int64_t var_28h @ rbp-0x28
│ ; var int64_t var_24h @ rbp-0x24
│ ; var int64_t canary @ rbp-0x18
│ 0x00400756 55 push rbp
│ 0x00400757 4889e5 mov rbp, rsp
│ 0x0040075a 53 push rbx
│ 0x0040075b 4883ec38 sub rsp, 0x38
│ 0x0040075f 64488b042528. mov rax, qword fs:[0x28]
│ 0x00400768 488945e8 mov qword [canary], rax
│ 0x0040076c 31c0 xor eax, eax
│ 0x0040076e c745c0000000. mov dword [var_40h], 0
│ ; CODE XREF from main @ 0x4007c5
│ ┌─> 0x00400775 8b45c0 mov eax, dword [var_40h]
│ ╎ 0x00400778 4863d8 movsxd rbx, eax
│ ╎ 0x0040077b bfa0106000 mov edi, obj.s ; 0x6010a0 ; "c61b68366edeb7bdce3c6820314b7498" ; const char *s
│ ╎ 0x00400780 e85bfeffff call sym.imp.strlen ; size_t strlen(const char *s)
│ ╎ 0x00400785 4839c3 cmp rbx, rax
│ ┌──< 0x00400788 733d jae 0x4007c7
│ │╎ 0x0040078a 8b45c0 mov eax, dword [var_40h]
│ │╎ 0x0040078d 8d500a lea edx, [rax + 0xa]
│ │╎ 0x00400790 8b45c0 mov eax, dword [var_40h]
│ │╎ 0x00400793 4898 cdqe
│ │╎ 0x00400795 0fb680a01060. movzx eax, byte [rax + obj.s] ; [0x6010a0:1]=99 ; "c61b68366edeb7bdce3c6820314b7498"
│ │╎ 0x0040079c 89c1 mov ecx, eax
│ │╎ 0x0040079e 8b45c0 mov eax, dword [var_40h]
│ │╎ 0x004007a1 83e001 and eax, 1
│ │╎ 0x004007a4 85c0 test eax, eax
│ ┌───< 0x004007a6 7407 je 0x4007af
│ ││╎ 0x004007a8 b801000000 mov eax, 1
│ ┌────< 0x004007ad eb05 jmp 0x4007b4
│ │││╎ ; CODE XREF from main @ 0x4007a6
│ │└───> 0x004007af b8ffffffff mov eax, 0xffffffff ; -1
│ │ │╎ ; CODE XREF from main @ 0x4007ad
│ └────> 0x004007b4 01c8 add eax, ecx
│ │╎ 0x004007b6 89c1 mov ecx, eax
│ │╎ 0x004007b8 4863c2 movsxd rax, edx
│ │╎ 0x004007bb 8888e0106000 mov byte [rax + obj.t], cl ; [0x6010e0:1]=83 ; "SharifCTF{????????????????????????????????}"
│ │╎ 0x004007c1 8345c001 add dword [var_40h], 1
│ │└─< 0x004007c5 ebae jmp 0x400775
│ │ ; CODE XREF from main @ 0x400788
│ └──> 0x004007c7 48b82f746d70. movabs rax, 0x616c662f706d742f ; '/tmp/fla'
│ 0x004007d1 488945d0 mov qword [filename], rax
│ 0x004007d5 c745d8672e74. mov dword [var_28h], 0x78742e67 ; 'g.tx'
│ 0x004007dc 66c745dc7400 mov word [var_24h], 0x74 ; 't' ; 116
│ 0x004007e2 488d45d0 lea rax, [filename]
│ 0x004007e6 be74094000 mov esi, 0x400974 ; const char *mode
│ 0x004007eb 4889c7 mov rdi, rax ; const char *filename
│ 0x004007ee e85dfeffff call sym.imp.fopen ; file*fopen(const char *filename, const char *mode)
│ 0x004007f3 488945c8 mov qword [stream], rax
│ 0x004007f7 488b45c8 mov rax, qword [stream]
│ 0x004007fb ba20116000 mov edx, obj.u ; 0x601120 ; "*******************************************" ; ...
│ 0x00400800 be76094000 mov esi, 0x400976 ; const char *format
│ 0x00400805 4889c7 mov rdi, rax ; FILE *stream
│ 0x00400808 b800000000 mov eax, 0
│ 0x0040080d e80efeffff call sym.imp.fprintf ; int fprintf(FILE *stream, const char *format, ...)
│ 0x00400812 c745c4000000. mov dword [var_3ch], 0
│ ; CODE XREF from main @ 0x4008b0
│ ┌─> 0x00400819 8b45c4 mov eax, dword [var_3ch]
│ ╎ 0x0040081c 4863d8 movsxd rbx, eax
│ ╎ 0x0040081f bfe0106000 mov edi, obj.t ; 0x6010e0 ; "SharifCTF{????????????????????????????????}" ; const char *s
│ ╎ 0x00400824 e8b7fdffff call sym.imp.strlen ; size_t strlen(const char *s)
│ ╎ 0x00400829 4839c3 cmp rbx, rax
│ ┌──< 0x0040082c 0f8383000000 jae 0x4008b5
│ │╎ 0x00400832 8b45c4 mov eax, dword [var_3ch]
│ │╎ 0x00400835 4898 cdqe
│ │╎ 0x00400837 8b0485601160. mov eax, dword [rax*4 + obj.p] ; [0x601160:4]=30
│ │╎ 0x0040083e 4863c8 movsxd rcx, eax
│ │╎ 0x00400841 488b45c8 mov rax, qword [stream]
│ │╎ 0x00400845 ba00000000 mov edx, 0 ; int whence
│ │╎ 0x0040084a 4889ce mov rsi, rcx ; long offset
│ │╎ 0x0040084d 4889c7 mov rdi, rax ; FILE *stream
│ │╎ 0x00400850 e8ebfdffff call sym.imp.fseek ; int fseek(FILE *stream, long offset, int whence)
│ │╎ 0x00400855 8b45c4 mov eax, dword [var_3ch]
│ │╎ 0x00400858 4898 cdqe
│ │╎ 0x0040085a 8b0485601160. mov eax, dword [rax*4 + obj.p] ; [0x601160:4]=30
│ │╎ 0x00400861 4898 cdqe
│ │╎ 0x00400863 0fb680e01060. movzx eax, byte [rax + obj.t] ; [0x6010e0:1]=83 ; "SharifCTF{????????????????????????????????}"
│ │╎ 0x0040086a 0fbec0 movsx eax, al
│ │╎ 0x0040086d 488b55c8 mov rdx, qword [stream]
│ │╎ 0x00400871 4889d6 mov rsi, rdx ; FILE *stream
│ │╎ 0x00400874 89c7 mov edi, eax ; int c
│ │╎ 0x00400876 e885fdffff call sym.imp.fputc ; int fputc(int c, FILE *stream)
│ │╎ 0x0040087b 488b45c8 mov rax, qword [stream]
│ │╎ 0x0040087f ba00000000 mov edx, 0 ; int whence
│ │╎ 0x00400884 be00000000 mov esi, 0 ; long offset
│ │╎ 0x00400889 4889c7 mov rdi, rax ; FILE *stream
│ │╎ 0x0040088c e8affdffff call sym.imp.fseek ; int fseek(FILE *stream, long offset, int whence)
│ │╎ 0x00400891 488b45c8 mov rax, qword [stream]
│ │╎ 0x00400895 ba20116000 mov edx, obj.u ; 0x601120 ; "*******************************************" ; ...
│ │╎ 0x0040089a be76094000 mov esi, 0x400976 ; const char *format
│ │╎ 0x0040089f 4889c7 mov rdi, rax ; FILE *stream
│ │╎ 0x004008a2 b800000000 mov eax, 0
│ │╎ 0x004008a7 e874fdffff call sym.imp.fprintf ; int fprintf(FILE *stream, const char *format, ...)
│ │╎ 0x004008ac 8345c401 add dword [var_3ch], 1
│ │└─< 0x004008b0 e964ffffff jmp 0x400819
│ │ ; CODE XREF from main @ 0x40082c
│ └──> 0x004008b5 488b45c8 mov rax, qword [stream]
│ 0x004008b9 4889c7 mov rdi, rax ; FILE *stream
│ 0x004008bc e80ffdffff call sym.imp.fclose ; int fclose(FILE *stream)
│ 0x004008c1 488d45d0 lea rax, [filename]
│ 0x004008c5 4889c7 mov rdi, rax ; const char *filename
│ 0x004008c8 e8f3fcffff call sym.imp.remove ; int remove(const char *filename)
│ 0x004008cd b800000000 mov eax, 0
│ 0x004008d2 488b5de8 mov rbx, qword [canary]
│ 0x004008d6 6448331c2528. xor rbx, qword fs:[0x28]
│ ┌─< 0x004008df 7405 je 0x4008e6
│ │ 0x004008e1 e80afdffff call sym.imp.__stack_chk_fail ; void __stack_chk_fail(void)
│ │ ; CODE XREF from main @ 0x4008df
│ └─> 0x004008e6 4883c438 add rsp, 0x38
│ 0x004008ea 5b pop rbx
│ 0x004008eb 5d pop rbp
└ 0x004008ec c3 ret
px
命令查看十六进制内容px
offset - 0 1 2 3 4 5 6 7 8 9 A B C D E F 0123456789ABCDEF
0x00400756 5548 89e5 5348 83ec 3864 488b 0425 2800 UH..SH..8dH..%(.
0x00400766 0000 4889 45e8 31c0 c745 c000 0000 008b ..H.E.1..E......
0x00400776 45c0 4863 d8bf a010 6000 e85b feff ff48 E.Hc....`..[...H
0x00400786 39c3 733d 8b45 c08d 500a 8b45 c048 980f 9.s=.E..P..E.H..
0x00400796 b680 a010 6000 89c1 8b45 c083 e001 85c0 ....`....E......
0x004007a6 7407 b801 0000 00eb 05b8 ffff ffff 01c8 t...............
0x004007b6 89c1 4863 c288 88e0 1060 0083 45c0 01eb ..Hc.....`..E...
0x004007c6 ae48 b82f 746d 702f 666c 6148 8945 d0c7 .H./tmp/flaH.E..
0x004007d6 45d8 672e 7478 66c7 45dc 7400 488d 45d0 E.g.txf.E.t.H.E.
0x004007e6 be74 0940 0048 89c7 e85d feff ff48 8945 [email protected]...]...H.E
0x004007f6 c848 8b45 c8ba 2011 6000 be76 0940 0048 .H.E.. .`[email protected]
0x00400806 89c7 b800 0000 00e8 0efe ffff c745 c400 .............E..
0x00400816 0000 008b 45c4 4863 d8bf e010 6000 e8b7 ....E.Hc....`...
0x00400826 fdff ff48 39c3 0f83 8300 0000 8b45 c448 ...H9........E.H
0x00400836 988b 0485 6011 6000 4863 c848 8b45 c8ba ....`.`.Hc.H.E..
0x00400846 0000 0000 4889 ce48 89c7 e8eb fdff ff8b ....H..H........
iz
命令可以查看程序中的字符串[0x00400756]> iz
[Strings]
nth paddr vaddr len size section type string
―――――――――――――――――――――――――――――――――――――――――――――――――――――――
0 0x000010a0 0x006010a0 32 33 .data ascii c61b68366edeb7bdce3c6820314b7498
1 0x000010e0 0x006010e0 43 44 .data ascii SharifCTF{????????????????????????????????}
2 0x00001120 0x00601120 43 44 .data ascii *******************************************
[0x00400756]> axt 0x6010a0
main 0x40077b [DATA] mov edi, obj.s
main 0x400795 [DATA] movzx eax, byte [rax + obj.s]
vv
命令进入r2 -d -A ./program
命令来进入调试器$ r2 -d -A ./e3dd9674429f4ce1a25c08ea799fc027
[x] Analyze all flags starting with sym. and entry0 (aa)
[x] Analyze function calls (aac)
[x] Analyze len bytes of instructions for references (aar)
[x] Finding and parsing C++ vtables (avrr)
[x] Skipping type matching analysis in debugger mode (aaft)
[x] Propagate noreturn information (aanr)
[x] Use -AA or aaaa to perform additional experimental analysis.
[0x7f8186b18050]>
db:断点,db后可以跟函数名或者地址
dbi:查看已有断点
dc:运行程序
dbt:查看堆栈
dr:查看寄存器
$ r2 -d -A ./e3dd9674429f4ce1a25c08ea799fc027
[x] Analyze all flags starting with sym. and entry0 (aa)
[x] Analyze function calls (aac)
[x] Analyze len bytes of instructions for references (aar)
[x] Finding and parsing C++ vtables (avrr)
[x] Skipping type matching analysis in debugger mode (aaft)
[x] Propagate noreturn information (aanr)
[x] Use -AA or aaaa to perform additional experimental analysis.
[0x7f53c8464050]> db main
[0x7f53c8464050]> dbi
0 0x00400756 E:1 T:0
[0x7f53c8464050]> dc
hit breakpoint at: 0x400756
[0x00400756]> dbt
0 0x400756 sp: 0x0 0 [main] main entry.init0+38
[0x00400756]> dr
rax = 0x00400756
rbx = 0x004008f0
rcx = 0x7f53c8443738
rdx = 0x7ffcee042568
r8 = 0x00000000
r9 = 0x7f53c84731f0
r10 = 0xfffffffffffffb8c
r11 = 0x7f53c829c730
r12 = 0x00400660
r13 = 0x00000000
r14 = 0x00000000
r15 = 0x00000000
rsi = 0x7ffcee042558
rdi = 0x00000001
rsp = 0x7ffcee042468
rbp = 0x00000000
rip = 0x00400756
rflags = 0x00000246
orax = 0xffffffffffffffff
r2pm -l
命令查看当前插件,r2的插件有很多,这里使用r2dec反编译插件来实现对程序的反编译,r2pm -install r2dec
来安装,安装完成后可以直接在r2中使用-A加载程序,然后使用r2dec反汇编程序,反汇编的命令是pdda
r2 -A ./e3dd9674429f4ce1a25c08ea799fc027
Analyze all flags starting with sym. and entry0 (aa)
Analyze function calls (aac)
Analyze len bytes of instructions for references (aar)
Check for vtables
Type matching analysis for all functions (aaft)
Propagate noreturn information
Use -AA or aaaa to perform additional experimental analysis.
s main
pdda
assembly | /* r2dec pseudo code output */
/* ./e3dd9674429f4ce1a25c08ea799fc027 @ 0x400756 */
#include <stdint.h>
(fcn) main () | int32_t main (void) {
int64_t var_40h;
int64_t var_3ch;
file* stream;
char * filename;
int64_t var_28h;
int64_t var_24h;
int64_t canary;
0x00400756 push rbp |
0x00400757 mov rbp, rsp |
0x0040075a push rbx |
0x0040075b sub rsp, 0x38 |
0x0040075f mov rax, qword fs:[0x28] | rax = *(fs:0x28);
0x00400768 mov qword [rbp - 0x18], rax | *((rbp - 0x18)) = rax;
0x0040076c xor eax, eax | eax = 0;
0x0040076e mov dword [rbp - 0x40], 0 | *((rbp - 0x40)) = 0;
do {
0x00400775 mov eax, dword [rbp - 0x40] | eax = *((rbp - 0x40));
0x00400778 movsxd rbx, eax | rbx = (int64_t) eax;
0x0040077b mov edi, 0x6010a0 |
0x00400780 call 0x4005e0 | rax = strlen ("c61b68366edeb7bdce3c6820314b7498");
0x00400785 cmp rbx, rax |
if (rbx >= rax) {
0x00400788 jae 0x4007c7 | goto label_0;
}
0x0040078a mov eax, dword [rbp - 0x40] | eax = *((rbp - 0x40));
0x0040078d lea edx, [rax + 0xa] | edx = rax + 0xa;
0x00400790 mov eax, dword [rbp - 0x40] | eax = *((rbp - 0x40));
0x00400793 cdqe | rax = (int64_t) eax;
0x00400795 movzx eax, byte [rax + 0x6010a0] | eax = *((rax + obj.s));
0x0040079c mov ecx, eax | ecx = eax;
0x0040079e mov eax, dword [rbp - 0x40] | eax = *((rbp - 0x40));
0x004007a1 and eax, 1 | eax &= 1;
0x004007a4 test eax, eax |
if (eax != 0) {
0x004007a6 je 0x4007af |
0x004007a8 mov eax, 1 | eax = 1;
0x004007ad jmp 0x4007b4 |
} else {
0x004007af mov eax, 0xffffffff | eax = 0xffffffff;
}
0x004007b4 add eax, ecx | eax += ecx;
0x004007b6 mov ecx, eax | ecx = eax;
0x004007b8 movsxd rax, edx | rax = (int64_t) edx;
0x004007bb mov byte [rax + 0x6010e0], cl | *((rax + obj.t)) = cl;
0x004007c1 add dword [rbp - 0x40], 1 | *((rbp - 0x40))++;
0x004007c5 jmp 0x400775 |
} while (1);
label_0:
0x004007c7 movabs rax, 0x616c662f706d742f | rax = 0x616c662f706d742f;
0x004007d1 mov qword [rbp - 0x30], rax | *((rbp - 0x30)) = rax;
0x004007d5 mov dword [rbp - 0x28], 0x78742e67 | *((rbp - 0x28)) = 0x78742e67;
0x004007dc mov word [rbp - 0x24], 0x74 | *((rbp - 0x24)) = 0x74;
0x004007e2 lea rax, [rbp - 0x30] | rax = rbp - 0x30;
0x004007e6 mov esi, 0x400974 |
0x004007eb mov rdi, rax |
0x004007ee call 0x400650 | rax = fopen (rax, 0x400974);
0x004007f3 mov qword [rbp - 0x38], rax | *((rbp - 0x38)) = rax;
0x004007f7 mov rax, qword [rbp - 0x38] | rax = *((rbp - 0x38));
0x004007fb mov edx, 0x601120 | edx = "*******************************************";
0x00400800 mov esi, 0x400976 |
0x00400805 mov rdi, rax |
0x00400808 mov eax, 0 | eax = 0;
0x0040080d call 0x400620 | fprintf (rax, 0x400976);
0x00400812 mov dword [rbp - 0x3c], 0 | *((rbp - 0x3c)) = 0;
do {
0x00400819 mov eax, dword [rbp - 0x3c] | eax = *((rbp - 0x3c));
0x0040081c movsxd rbx, eax | rbx = (int64_t) eax;
0x0040081f mov edi, 0x6010e0 |
0x00400824 call 0x4005e0 | rax = strlen ("SharifCTF{????????????????????????????????}");
0x00400829 cmp rbx, rax |
if (rbx >= rax) {
0x0040082c jae 0x4008b5 | goto label_1;
}
0x00400832 mov eax, dword [rbp - 0x3c] | eax = *((rbp - 0x3c));
0x00400835 cdqe | rax = (int64_t) eax;
0x00400837 mov eax, dword [rax*4 + 0x601160] | eax = *((rax*4 + obj.p));
0x0040083e movsxd rcx, eax | rcx = (int64_t) eax;
0x00400841 mov rax, qword [rbp - 0x38] | rax = *((rbp - 0x38));
0x00400845 mov edx, 0 |
0x0040084a mov rsi, rcx |
0x0040084d mov rdi, rax |
0x00400850 call 0x400640 | fseek (rax, rcx, 0);
0x00400855 mov eax, dword [rbp - 0x3c] | eax = *((rbp - 0x3c));
0x00400858 cdqe | rax = (int64_t) eax;
0x0040085a mov eax, dword [rax*4 + 0x601160] | eax = *((rax*4 + obj.p));
0x00400861 cdqe | rax = (int64_t) eax;
0x00400863 movzx eax, byte [rax + 0x6010e0] | eax = *((rax + obj.t));
0x0040086a movsx eax, al | eax = (int32_t) al;
0x0040086d mov rdx, qword [rbp - 0x38] | rdx = *((rbp - 0x38));
0x00400871 mov rsi, rdx |
0x00400874 mov edi, eax |
0x00400876 call 0x400600 | fputc (eax, *((rbp - 0x38)));
0x0040087b mov rax, qword [rbp - 0x38] | rax = *((rbp - 0x38));
0x0040087f mov edx, 0 | edx = 0;
0x00400884 mov esi, 0 |
0x00400889 mov rdi, rax |
0x0040088c call 0x400640 | fseek (rax, 0, edx);
0x00400891 mov rax, qword [rbp - 0x38] | rax = *((rbp - 0x38));
0x00400895 mov edx, 0x601120 | edx = "*******************************************";
0x0040089a mov esi, 0x400976 |
0x0040089f mov rdi, rax |
0x004008a2 mov eax, 0 | eax = 0;
0x004008a7 call 0x400620 | fprintf (rax, 0x400976);
0x004008ac add dword [rbp - 0x3c], 1 | *((rbp - 0x3c))++;
0x004008b0 jmp 0x400819 |
} while (1);
label_1:
0x004008b5 mov rax, qword [rbp - 0x38] | rax = *((rbp - 0x38));
0x004008b9 mov rdi, rax |
0x004008bc call 0x4005d0 | fclose (*((rbp - 0x38)));
0x004008c1 lea rax, [rbp - 0x30] | rax = rbp - 0x30;
0x004008c5 mov rdi, rax |
0x004008c8 call 0x4005c0 | remove (rax);
0x004008cd mov eax, 0 | eax = 0;
0x004008d2 mov rbx, qword [rbp - 0x18] | rbx = *((rbp - 0x18));
0x004008d6 xor rbx, qword fs:[0x28] | rbx ^= *(fs:0x28);
if (*((rbp - 0x3c)) != 0) {
0x004008df je 0x4008e6 |
0x004008e1 call 0x4005f0 | stack_chk_fail ();
}
0x004008e6 add rsp, 0x38 |
0x004008ea pop rbx |
0x004008eb pop rbp |
0x004008ec ret | return rax;
}
0x04 题目实例
int __cdecl main(int argc, const char **argv, const char **envp)
{
char v3; // al
int i; // [rsp+0h] [rbp-40h]
int j; // [rsp+4h] [rbp-3Ch]
FILE *stream; // [rsp+8h] [rbp-38h]
char filename[24]; // [rsp+10h] [rbp-30h] BYREF
unsigned __int64 v9; // [rsp+28h] [rbp-18h]
v9 = __readfsqword(0x28u);
for ( i = 0; i < strlen(s); ++i )
{
if ( (i & 1) != 0 )
v3 = 1;
else
v3 = -1;
*(&t + i + 10) = s[i] + v3;
}
strcpy(filename, "/tmp/flag.txt");
stream = fopen(filename, "w");
fprintf(stream, "%sn", u);
for ( j = 0; j < strlen(&t); ++j )
{
fseek(stream, p[j], 0);
fputc(*(&t + p[j]), stream);
fseek(stream, 0LL, 0);
fprintf(stream, "%sn", u);
}
fclose(stream);
remove(filename);
return 0;
}
0x05 总结
参考文章:
https://wizardforcel.gitbooks.io/100-gdb-tips/content/print-registers.html
https://linuxtools-rst.readthedocs.io/zh_CN/latest/tool/gdb.html
https://linux.cn/article-13074-1.html
E
N
D
关
于
我
们
Tide安全团队正式成立于2019年1月,是新潮信息旗下以互联网攻防技术研究为目标的安全团队,团队致力于分享高质量原创文章、开源安全工具、交流安全技术,研究方向覆盖网络攻防、系统安全、Web安全、移动终端、安全开发、物联网/工控安全/AI安全等多个领域。
团队作为“省级等保关键技术实验室”先后与哈工大、齐鲁银行、聊城大学、交通学院等多个高校名企建立联合技术实验室。团队公众号自创建以来,共发布原创文章370余篇,自研平台达到26个,目有15个平台已开源。此外积极参加各类线上、线下CTF比赛并取得了优异的成绩。如有对安全行业感兴趣的小伙伴可以踊跃加入或关注我们。
原文始发于微信公众号(Tide安全团队):动态调试elf文件的几种方法
免责声明:文章中涉及的程序(方法)可能带有攻击性,仅供安全研究与教学之用,读者将其信息做其他用途,由读者承担全部法律及连带责任,本站不承担任何法律及连带责任;如有问题可邮件联系(建议使用企业邮箱或有效邮箱,避免邮件被拦截,联系方式见首页),望知悉。
- 左青龙
- 微信扫一扫
-
- 右白虎
- 微信扫一扫
-
评论