def log_api_info(p, api_name): if api_name in p.emu.winapi_info_dict: print(Fore.LIGHTRED_EX + api_name) api_info = p.emu.winapi_info_dict[api_name] arg_idx = 0 for arg_type in api_info["args_types"]: arg_idx += 1 arg_raw = int.from_bytes( p.uc_eng.mem_read( p.uc_eng.reg_read(UC_X86_REG_ESP) + (4 * (arg_idx)), 4), "little") arg = "" if "wchar*" in arg_type: arg = read_mem_string(p.uc_eng, arg_raw, 2, 50) elif "char*" in arg_type: arg = read_mem_string(p.uc_eng, arg_raw, 1, 50) else: arg = str(hex(arg_raw)) if arg: if arg[-1] == "\n": arg = arg[:-1] else: arg = "NULL" print(Fore.BLUE + " " + "[" + arg_type + "]" + " > " + arg) else: print(Fore.LIGHTRED_EX + api_name + "\tcalled") pass
def InternetOpen(self, proc, argv, ctx={}): """ void InternetOpenA( LPTSTR lpszAgent, DWORD dwAccessType, LPTSTR lpszProxy, LPTSTR lpszProxyBypass, DWORD dwFlags ); """ ua, access, proxy, bypass, flags = argv cw = common.get_char_width(ctx) if ua: ua = common.read_mem_string(proc.uc_eng, ua, cw) argv[0] = ua if proxy: proxy = common.read_mem_string(proc.uc_eng, proxy, cw) argv[2] = proxy if bypass: bypass = common.read_mem_string(proc.uc_eng, bypass, cw) argv[3] = bypass inet_handle = proc.emu.net_manager.create_inet_inst(ua, proxy, bypass) return inet_handle
def InternetOpenUrl(self, proc, argv, ctx={}): """ void InternetOpenUrlA( HINTERNET hInternet, LPCSTR lpszUrl, LPCSTR lpszHeaders, DWORD dwHeadersLength, DWORD dwFlags, DWORD_PTR dwContext ); """ hInternet, lpszUrl, lpszHeaders, dwHeadersLength, dwFlags, dwContext = argv cw = ApiHandler.get_char_width(ctx) if lpszUrl: url = common.read_mem_string(proc.uc_eng, lpszUrl, cw) argv[1] = url if lpszHeaders: hdrs = {} headers = common.read_mem_string(proc.uc_eng, lpszHeaders, cw) _headers = headers.split("\r\n") for header in _headers: k, v = header.split(":") if v[0] == " ": v = v[1:] hdrs[k] = v argv[2] = headers defs = windefs.get_flag_defines(dwFlags) argv[4] = ' | '.join(defs) crack = urlparse(url) if crack.scheme == "http": # FIXME : parse port in url netloc port = 80 else: port = 443 http_conn_handle = proc.emu.net_manager.create_connection( inet_handle=hInternet, host=crack.netloc, # host flag=dwFlags, ctx=dwContext, port=port) http_req_handle = proc.emu.net_manager.create_http_request( http_conn_handle, crack.path, flag=dwFlags) http_req = obj_manager.ObjectManager.get_obj_by_handle(http_req_handle) if hdrs: http_req.add_headers(hdrs) proc.emu.net_manager.send_http_request(http_req_handle, None) return http_req_handle
def CreateProcess(self, proc, argv, ctx={}): '''BOOL CreateProcess( LPTSTR lpApplicationName, LPTSTR lpCommandLine, LPSECURITY_ATTRIBUTES lpProcessAttributes, LPSECURITY_ATTRIBUTES lpThreadAttributes, BOOL bInheritHandles, DWORD dwCreationFlags, LPVOID lpEnvironment, LPTSTR lpCurrentDirectory, LPSTARTUPINFO lpStartupInfo, LPPROCESS_INFORMATION lpProcessInformation );''' app, cmd, pa, ta, inherit, flags, env, cd, si, ppi = argv cw = self.get_char_width(ctx) cmdstr = '' appstr = '' if app: appstr = common.read_mem_string(proc.uc_eng, app, cw) argv[0] = appstr if cmd: cmdstr = common.read_mem_string(proc.uc_eng, cmd, cw) argv[1] = cmdstr if not appstr and cmdstr: appstr = cmdstr elif appstr and cmdstr: appstr += " "+cmdstr # cmdstr be param elif appstr and not cmdstr: pass else: return 0 # child proc can't be inherited new_proc_obj = proc.emu.create_process(appstr) main_thread = obj_manager.ObjectManager.get_obj_by_handle(new_proc_obj.threads[-1]) proc.emu.push_wait_queue(new_proc_obj) _pi = self.k32types.PROCESS_INFORMATION(proc.ptr_size) data = common.mem_cast(proc.uc_eng, _pi, ppi) _pi.hProcess = new_proc_obj.handle _pi.hThread = main_thread.handle _pi.dwProcessId = new_proc_obj.pid _pi.dwThreadId = main_thread.tid proc.uc_eng.mem_write(ppi, common.get_bytes(data)) rv = 1 return rv
def CreateFileMapping(self, proc, argv, ctx={}): ''' HANDLE CreateFileMapping( HANDLE hFile, LPSECURITY_ATTRIBUTES lpFileMappingAttributes, DWORD flProtect, DWORD dwMaximumSizeHigh, DWORD dwMaximumSizeLow, LPTSTR lpName ); ''' hfile, map_attrs, prot, max_size_high, max_size_low, map_name = argv cw = self.get_char_width(ctx) if prot & memdef.PAGE_TYPE.MEM_IMAGE: prot = memdef.PAGE_TYPE.MEM_IMAGE # Get to full map size map_size = (max_size_high << 32) | max_size_low name = '' if map_name: name = common.read_mem_string(proc.uc_eng, map_name, cw) argv[5] = name mmf_handle = proc.emu.fs_manager.create_file_mapping(hfile, map_size, prot, name) return mmf_handle
def wcscat(self, proc, argv, ctx={}): ''' wchar_t *wcscat( wchar_t *strDestination, const wchar_t *strSource ); ''' _str1, _str2 = argv s1 = common.read_mem_string(proc.uc_eng, _str1, 2) s2 = common.read_mem_string(proc.uc_eng, _str2, 2) argv[0] = s1 argv[1] = s2 new = (s1 + s2).encode('utf-16le') proc.uc_eng.mem_write(_str1, new + b'\x00\x00') return _str1
def OutputDebugString(self, proc, argv, ctx={}): ''' void OutputDebugStringA( LPCSTR lpOutputString ); ''' _str, = argv cw = common.get_char_width(ctx) argv[0] = common.read_mem_string(proc.uc_eng, _str, cw)
def URLDownloadToFile(self, proc, argv, ctx={}): """ HRESULT URLDownloadToFile( LPUNKNOWN pCaller, LPCTSTR szURL, LPCTSTR szFileName, DWORD dwReserved, LPBINDSTATUSCALLBACK lpfnCB ); """ pCaller, szURL, szFileName, dwReserved, lpfnCB = argv cw = common.get_char_width(ctx) if szURL: url = common.read_mem_string(proc.uc_eng, szURL, cw) argv[1] = url ps_url = urlparse(url) if szFileName: name = common.read_mem_string(proc.uc_eng, szFileName, cw) argv[2] = name inet_inst_handle = proc.emu.net_manager.create_inet_inst( agent="Default") if ps_url.scheme == "https": port = 443 if ps_url.scheme == "http": port = 80 http_conn_handle = proc.emu.net_manager.create_connection( inet_inst_handle, host=ps_url.netloc, port=port) if not http_conn_handle or http_conn_handle == 0xFFFFFFFF: rv = windefs.INET_E_DOWNLOAD_FAILURE else: http_req_handle = proc.emu.net_manager.create_http_request( http_conn_handle, url) proc.emu.net_manager.send_http_request(http_req_handle, None) rv = windefs.ERROR_SUCCESS buf = proc.emu.net_manager.recv_http_response(http_req_handle, 0) return rv
def strlen(self, proc, argv, ctx={}): """ size_t strlen( const char *str ); """ s, = argv string = common.read_mem_string(proc.uc_eng, s, 1) argv[0] = string rv = len(string) return rv
def LoadLibrary(self, proc, argv, ctx={}): '''HMODULE LoadLibrary( LPTSTR lpLibFileName );''' lib_name, = argv hmod = windefs.NULL cw = common.get_char_width(ctx) req_lib = common.read_mem_string(proc.uc_eng, lib_name, cw) lib = ApiHandler.api_set_schema(req_lib) hmod = proc.load_library(lib) argv[0] = req_lib return hmod
def lstrlen(self, proc, argv, ctx={}): ''' int lstrlen( LPCSTR lpString ); ''' src, = argv try: cw = common.get_char_width(ctx) except Exception: cw = 1 s = common.read_mem_string(proc.uc_eng, src, cw) argv[0] = s return len(s)
def WinExec(self, proc, argv, ctx={}): ''' UINT WinExec( LPCSTR lpCmdLine, UINT uCmdShow ); ''' lpCmdLine, uCmdShow = argv rv = 1 if lpCmdLine: cmd = common.read_mem_string(proc.uc_eng, lpCmdLine, 1) argv[0] = cmd app = cmd.split()[0] #proc = proc.create_process(path=app, cmdline=cmd) #self.log_process_event(app, 'create') rv = 32 return rv
def LoadLibraryEx(self, proc, argv, ctx={}): '''HMODULE LoadLibraryExA( LPCSTR lpLibFileName, HANDLE hFile, DWORD dwFlags );''' lib_name, _, dwFlags = argv hmod = 0 cw = common.get_char_width(ctx) req_lib = common.read_mem_string(proc.uc_eng, lib_name, cw) lib = ApiHandler.api_set_schema(req_lib) hmod = proc.load_library(lib) flags = { 0x1: 'DONT_RESOLVE_DLL_REFERENCES', 0x10: 'LOAD_IGNORE_CODE_AUTHZ_LEVEL', 0x2: 'LOAD_LIBRARY_AS_DATAFILE', 0x40: 'LOAD_LIBRARY_AS_DATAFILE_EXCLUSIVE', 0x20: 'LOAD_LIBRARY_AS_IMAGE_RESOURCE', 0x200: 'LOAD_LIBRARY_SEARCH_APPLICATION_DIR', 0x1000: 'LOAD_LIBRARY_SEARCH_DEFAULT_DIRS', 0x100: 'LOAD_LIBRARY_SEARCH_DLL_LOAD_DIR', 0x800: 'LOAD_LIBRARY_SEARCH_SYSTEM32', 0x400: 'LOAD_LIBRARY_SEARCH_USER_DIRS', 0x8: 'LOAD_WITH_ALTERED_SEARCH_PATH', } pretty_flags = ' | '.join([name for bit, name in flags.items() if dwFlags & bit]) argv[0] = req_lib argv[1] = argv[1] argv[2] = pretty_flags if not hmod: proc.set_last_error(windefs.ERROR_MOD_NOT_FOUND) return hmod
def CreateFile(self, proc, argv, ctx={}): ''' HANDLE CreateFile( LPTSTR lpFileName, DWORD dwDesiredAccess, DWORD dwShareMode, LPSECURITY_ATTRIBUTES lpSecurityAttributes, DWORD dwCreationDisposition, DWORD dwFlagsAndAttributes, HANDLE hTemplateFile ); ''' pFileName, access, share, secAttr, disp, flags, template = argv cw = common.get_char_width(ctx) f_name = common.read_mem_string(proc.uc_eng, pFileName, cw) py_io_mode = proc.emu.fs_manager.convert_io_mode(f_name, access, disp) file_handle = proc.emu.fs_manager.create_file(f_name, py_io_mode) return file_handle
def GetModuleHandle(self, proc, argv, ctx={}): '''HMODULE GetModuleHandle( LPCSTR lpModuleName );''' mod_name, = argv cw = self.get_char_width(ctx) rv = 0 if not mod_name: rv = proc.image_base else: lib = common.read_mem_string(proc.uc_eng, mod_name, cw) if lib not in proc.imp: lib = ApiHandler.api_set_schema(lib) if lib in proc.imp: rv = pydll.SYSTEM_DLL_BASE[lib] else: rv = 0 return rv
def printf(self, proc, argv, ctx={}): arch = proc.get_arch() if arch == UC_ARCH_X86: fmt, va_list = ApiHandler.get_argv(proc, cv.CALL_CONV_CDECL, 2)[:2] else: raise Exception("Unsupported architecture") rv = 0 fmt_str = common.read_mem_string(proc.uc_eng, fmt, 1) fmt_cnt = self.get_va_arg_count(fmt_str) vargs = self.va_args2(proc, fmt_cnt) fin = common.make_fmt_str(proc, fmt_str, vargs) rv = len(fin) argv.append(fin) # print(fin) return rv
def __stdio_common_vfprintf(self, proc, argv, ctx={}): arch = proc.get_arch() if arch == UC_ARCH_X86: opts, opts2, stream, fmt, _, va_list = ApiHandler.get_argv( proc, cv.CALL_CONV_CDECL, 6)[:6] else: raise Exception("Unsupported architecture") rv = 0 fmt_str = common.read_mem_string(proc.uc_eng, fmt, 1) fmt_cnt = self.get_va_arg_count(fmt_str) vargs = self.va_args(va_list, fmt_cnt) fin = common.make_fmt_str(proc, fmt_str, vargs) argv[:] = [opts, stream, fin] # print(fin) rv = len(fin) return rv