def main(filepath): if check_strip() and check_exe(): clear_code() init = Init(filepath) init.disassemble() init.process() init.ailProcess() else: sys.stderr.write( 'Error: binary is not stripped or is a shared library\n')
def main(): if not check_exe(): with open('final.s') as f: contents = f.readlines() task1() task2() contents = task3_4() # task5() # write back with open('final.s', 'w') as f: f.writelines(contents)
def main(filepath, is_32): global step step = 1 if is_32: if check_exe(): # executable t = text_process_strip(filepath) while t == False: t = text_process_strip(filepath) else: # shared object don't translate target addrs into # GLOBAL_OFFSET_TABLE, instead, dump the thunk addr for # analysis in share_lib_helper.ml addr = thunk_identify(filepath).strip() with open('pic_thunk.info', 'w') as f: f.write(addr + '\n')
def check(filepath, assumptions): if not assumptions: assumptions = [] if not os.path.isfile(filepath): print "cannot find input binary" return False if os.path.dirname(filepath) != os.getcwd(): shutil.copy(filepath, '.') os.system('file ' + filepath + ' > elf.info') if not check_exe(): print "Uroboros doesn't support shared library" return False # if assumption three is utilized, then input binary must be unstripped. if '3' in assumptions and not check_strip(): print 'Uroboros does not support stripped binaries when using assumption three' return False return True
def main(): with open("final.s") as f: lines = f.readlines() is_32 = check_32() ll = len(lines) main_symbol = "" find_text = False for i in range(ll): l = lines[i] if ".text" in l: if find_text == False: find_text = True else: l = l.replace(".text:", "") if "lea 0x0(%esi," in l: if ':' in l: label = l.split(':')[0] # label: lea 0x0.... l = label + " : nop;nop;nop;nop;nop;nop;nop;\n" else: l = "nop;nop;nop;nop;nop;nop;nop;\n" elif "lea 0x0(%edi," in l: if ':' in l: label = l.split(':')[0] # label: lea 0x0.... l = label + " : nop;nop;nop;nop;nop;nop;nop;\n" else: label = "" l = "nop;nop;nop;nop;nop;nop;nop;\n" # __gmon_start__ symbol is resolved by the linked program itself, it surely can not be resolved # in our final.s code, just remove it elif "__gmon_start__" in l: l = "" elif "lea 0x7FFFFFFC(,%ebx,0x4),%edi" in l: l = l.replace('0x7FFFFFFC', '0x7FFFFFFFFFFFFFFC') elif "repz retq" in l: l = l.replace("repz retq", "repz\nretq\n") elif "repz ret" in l: l = l.replace("repz ret", "repz\nret\n") elif "repz pop" in l: l = l.replace("repz pop", "repz\npop") elif "movzbl $S_" in l: l = l.replace("movzbl $S_", "movzbl S_") # Warning: indirect jmp without `*' # the exe crashes at this instruction # adjust it into jmp S_0x4006C1 elif "jmpq " in l and "*" not in l: l = l.replace('jmpq ', 'jmp ') elif "__libc_start_main" in l and is_32 == True: main_symbol = lines[i - 1].split()[1] lines[i - 1] = lines[i - 1].replace(main_symbol, "main") main_symbol = main_symbol[1:].strip() elif is_32 == False and "__libc_start_main" in l: main_symbol = lines[i - 1].split()[-1].split(',')[0] lines[i - 1] = lines[i - 1].replace(main_symbol, "main") main_symbol = main_symbol[1:].strip() lines[i] = l #print main_symbol ## Some of the PIC code/module rely on typical pattern to locate ## such as: ## 804c460: push %ebx ## 804c461: call 804c452 <__i686.get_pc_thunk.bx> ## 804c466: add $0x2b8e,%ebx ## 804c46c: sub $0x18,%esp ## What we can do this pattern match `<__i686.get_pc_thunk.bx>` and calculate ## the address by plusing 0x2b8e and 0x804c466, which equals to the begin address of GOT.PLT table ## symbols can be leveraged in re-assemble are ## _GLOBAL_OFFSET_TABLE_ == ** .got.plt ** ## .... if check_exe(): mains = [] main_symbol1 = "" with open('main.info') as f: mains = f.readlines() main_symbol1 = mains[0].strip() def helpf(l): if main_symbol1 != "" and main_symbol1 in l: #main_s1 = "S"+main_symbol #if main_s1 in l: #l = l.replace(main_s1, ".globl main\nmain") l = ".globl main\nmain:\n" + l #else: #l = l.replace(main_symbol, ".globl main\nmain") # l = ".globl main\nmain:\n"+l return l #print lines lines = map(helpf, lines) #branch_routine :pop global_des #jmp *branch_des #lines.append('switch_bb: jmp *branch_des\n') with open("final.s", 'w') as f: f.writelines(lines) if os.path.isfile('inline_symbols.txt'): inline_update.main()
def post_process_data(): if not check_32(): # for 64-bit binaries, remember to align data sections with 16. if check_exe(): with open("final_data.s") as f: lines = f.readlines() ll = len(lines) for i in range(ll - 1): l = lines[i] if ".data" in l or ".bss" in l or ".rodata" in l: ln = lines[i + 1] if "align" not in ln: # add the align macro lines[i + 1] = ".align 16\n" + ln with open('final_data.s', 'w') as f: f.writelines(lines) else: if check_exe(): with open("final_data.s") as f: lines = f.readlines() ll = len(lines) in_rodata = False in_data = False #if ".section .rodata" in l: # for j in range(i+1, i+10): # lines[j] = "" #if ".section .data" in l: # for j in range(i+1, i+10): # lines[j] = "" # this variable is used by basic block flattern diverisfy # lines[i+1] = "global_des:\n" # lines[i+2] = ".byte 0x00\n" # lines[i+3] = ".byte 0x00\n" # lines[i+4] = ".byte 0x00\n" # lines[i+5] = ".byte 0x00\n" # lines[i+6] = "branch_des:\n" # lines[i+7] = ".byte 0x00\n" # lines[i+8] = ".byte 0x00\n" # lines[i+9] = ".byte 0x00\n" # lines[i+10] = ".byte 0x00\n" for i in range(ll): l = lines[i] if in_data == False and ".data" in l: in_data = True #lines[i+2] = "" #lines[i+3] = "" #lines[i+4] = "" #lines[i+5] = "" #lines[i+6] = "" #lines[i+7] = "" #lines[i+8] = "" #lines[i+9] = "" # this variable is used by basic block flattern diversify # please comment these lines if no bb flattern diversifying used # lines[i+1] = "global_des:\n" # lines[i+2] = ".byte 0x00\n" # lines[i+3] = ".byte 0x00\n" # lines[i+4] = ".byte 0x00\n" # lines[i+5] = ".byte 0x00\n" # lines[i+6] = "branch_des:\n.byte 0x00\n" # lines[i+7] = ".byte 0x00\n" # lines[i+8] = ".byte 0x00\n" # lines[i+9] = ".byte 0x00\n" elif in_rodata == False and ".rodata" in l: # add two instructions # branch_routine :pop global_des # jmp *branch_des in_rodata = True #lines[i+2] = "" #lines[i+3] = "" #lines[i+4] = "" #lines[i+5] = "" #lines[i+6] = "" #lines[i+7] = "" #lines[i+8] = "" #lines[i+9] = "" #lines[i+10] = "" elif ".bss" in l: #for j in range(i+2,i+44+2): # lines[j] = "" break with open('final_data.s', 'w') as f: f.writelines(lines)