Пример #1
0
    def on_message(self, message, data):
        if 'payload' not in message:
            print(message)
            return

        what = message['payload']
        parts = what.split(':::')
        if len(parts) < 2:
            print(what)
            return

        cmd = parts[0]
        if cmd == 'backtrace':
            if self.app.get_session_ui() is not None and self.app.get_backtrace_panel() is not None:
                try:
                    self.app.get_backtrace_panel().set_backtrace(json.loads(parts[1]))
                except:
                    pass
        elif cmd == 'emulator':
            # on a separate thread to allow js api recursion
            Thread(target=self.emulator.api, args=(parts[1:],)).start()
        elif cmd == 'enumerate_java_classes_start':
            if self.app.get_java_classes_panel() is not None:
                self.app.get_java_classes_panel().on_enumeration_start()
            if self.app.get_java_trace_panel() is not None:
                self.app.get_java_trace_panel().on_enumeration_start()
        elif cmd == 'enumerate_java_classes_match':
            if self.app.get_java_classes_panel() is not None:
                self.app.get_java_classes_panel().on_enumeration_match(parts[1])
            if self.app.get_java_trace_panel() is not None:
                self.app.get_java_trace_panel().on_enumeration_match(parts[1])
        elif cmd == 'enumerate_java_classes_complete':
            self.app_window.get_menu().on_java_classes_enumeration_complete()
            if self.app.get_java_classes_panel() is not None:
                self.app.get_java_classes_panel().on_enumeration_complete()
            if self.app.get_java_trace_panel() is not None:
                self.app.get_java_trace_panel().on_enumeration_complete()
        elif cmd == 'enumerate_java_methods_complete':
            self.bus.emit(parts[1], json.loads(parts[2]), parts[1])
        elif cmd == 'ftrace':
            if self.app.get_ftrace_panel() is not None:
                self.app.get_ftrace_panel().append_data(parts[1])
        elif cmd == 'enable_kernel':
            self.app_window.get_menu().enable_kernel_menu()
        elif cmd == 'hook_java_callback':
            h = Hook(Hook.HOOK_JAVA)
            h.set_ptr(1)
            h.set_input(parts[1])
            if self.java_pending_args:
                h.set_condition(self.java_pending_args['condition'])
                h.set_logic(self.java_pending_args['logic'])
                self.java_pending_args = None
            self.java_hooks[h.get_input()] = h
            self.app.get_hooks_panel().hook_java_callback(h)
        elif cmd == 'hook_native_callback':
            h = Hook(Hook.HOOK_NATIVE)
            h.set_ptr(int(parts[1], 16))
            h.set_input(self.temporary_input)
            h.set_bytes(binascii.unhexlify(parts[2]))
            self.temporary_input = ''
            if self.native_pending_args:
                h.set_condition(self.native_pending_args['condition'])
                h.set_logic(self.native_pending_args['logic'])
                self.native_pending_args = None
            self.hooks[h.get_ptr()] = h
            self.app.get_hooks_panel().hook_native_callback(h)
        elif cmd == 'hook_onload_callback':
            h = Hook(Hook.HOOK_ONLOAD)
            h.set_ptr(0)
            h.set_input(parts[1])

            self.on_loads[parts[1]] = h
            if self.app.session_ui is not None and self.app.get_hooks_panel() is not None:
                self.app.get_hooks_panel().hook_onload_callback(h)
        elif cmd == 'java_trace':
            panel = self.app.get_java_trace_panel()
            if panel is None:
                panel = self.app.get_session_ui().add_dwarf_tab(SessionUi.TAB_JAVA_TRACE)
            panel.on_event(parts[1], parts[2], parts[3])
        elif cmd == 'log':
            self.app.get_console_panel().get_js_console().log(parts[1])
        elif cmd == 'memory_scan_match':
            self.bus.emit(parts[1], parts[2], json.loads(parts[3]))
        elif cmd == 'memory_scan_complete':
            self.app_window.get_menu().on_bytes_search_complete()
            self.bus.emit(parts[1] + ' complete', 0, 0)
        elif cmd == 'onload_callback':
            self.loading_library = parts[1]
            self.app.get_console_panel().get_js_console().log('hook onload %s @thread := %s' % (
                parts[1], parts[3]))
            self.app.get_hooks_panel().hit_onload(parts[1], parts[2])
        elif cmd == 'release':
            if parts[1] in self.contexts:
                del self.contexts[parts[1]]
            self.app.on_tid_resumed(int(parts[1]))
        elif cmd == 'set_context':
            data = json.loads(parts[1])
            if 'context' in data:
                context = Context(data['context'])
                self.contexts[str(data['tid'])] = context

                sym = ''
                if 'pc' in context.__dict__:
                    name = data['ptr']
                    if context.pc.symbol_name is not None:
                        sym = '(%s - %s)' % (context.pc.symbol_module_name, context.pc.symbol_name)
                else:
                    name = data['ptr']
                self.app.get_contexts_lists_panel().add_context(data, library_onload=self.loading_library)
                # check if data['reason'] is 0 (REASON_HOOK)
                if self.loading_library is None and data['reason'] == 0:
                    self.log('hook %s %s @thread := %d' % (name, sym, data['tid']))
                if len(self.contexts.keys()) > 1 and self.app.get_context_panel().have_context():
                    return
                self.app.get_session_ui().request_session_ui_focus()
            else:
                self.arch = data['arch']
                self.pointer_size = data['pointerSize']
                self.java_available = data['java']
                self.app.get_console_panel().get_js_console().log('injected into := ' + str(self.pid))
                self.app_window.on_context_info()

            self.context_tid = data['tid']
            self.app.apply_context(data)
            if self.loading_library is not None:
                self.loading_library = None
        elif cmd == 'set_data':
            key = parts[1]
            if data:
                self.app.get_data_panel().append_data(key, hexdump(data, result='return'))
            else:
                self.app.get_data_panel().append_data(key, str(parts[2]))
        elif cmd == 'script_loaded':
            if self._spawned:
                self.device.resume(self.pid)
        elif cmd == 'tracer':
            panel = self.app.get_trace_panel()
            if panel is None:
                panel = self.app.get_session_ui().add_dwarf_tab(SessionUi.TAB_TRACE)
            if panel is not None:
                # safely checked later
                panel.start()

                trace_events_parts = parts[1].split(',')
                while len(trace_events_parts) > 0:
                    t = TraceEvent(trace_events_parts.pop(0),
                                   trace_events_parts.pop(0),
                                   trace_events_parts.pop(0),
                                   trace_events_parts.pop(0))
                    panel.event_queue.append(t)
        elif cmd == 'unhandled_exception':
            # todo
            pass
        elif cmd == 'update_modules':
            self.app.apply_context({'tid': parts[1], 'modules': json.loads(parts[2])})
        elif cmd == 'update_ranges':
            self.app.apply_context({'tid': parts[1], 'ranges': json.loads(parts[2])})
        elif cmd == 'watcher':
            exception = json.loads(parts[1])
            self.log('watcher hit op %s address %s @thread := %s' %
                     (exception['memory']['operation'], exception['memory']['address'], parts[2]))
        elif cmd == 'watcher_added':
            if self.app.get_watchers_panel() is not None:
                self.app.get_watchers_panel().add_watcher_callback(parts[1])
        elif cmd == 'watcher_removed':
            if self.app.get_watchers_panel() is not None:
                self.app.get_watchers_panel().remove_watcher_callback(parts[1])
        else:
            print(what)
Пример #2
0
    def _on_message(self, message, data):
        QApplication.processEvents()
        if 'payload' not in message:
            print('payload: ' + str(message))
            return

        what = message['payload']
        parts = what.split(':::')
        if len(parts) < 2:
            print(what)
            return

        cmd = parts[0]
        if cmd == 'api_ping_timeout':
            self._script.post({"type": str(parts[1])})
        elif cmd == 'backtrace':
            self.onBackTrace.emit(json.loads(parts[1]))
        elif cmd == 'class_loader_loading_class':
            str_fmt = ('@thread {0} loading class := {1}'.format(parts[1], parts[2]))
            self.log_event(str_fmt)
        elif cmd == 'emulator':
            self.onEmulator.emit(parts[1:])
        elif cmd == 'enumerate_java_classes_start':
            self.onEnumerateJavaClassesStart.emit()
        elif cmd == 'enumerate_java_classes_match':
            self.onEnumerateJavaClassesMatch.emit(parts[1])
        elif cmd == 'enumerate_java_classes_complete':
            self.onEnumerateJavaClassesComplete.emit()
        elif cmd == 'enumerate_java_methods_complete':
            self.onEnumerateJavaMethodsComplete.emit([parts[1], json.loads(parts[2])])
        elif cmd == 'ftrace':
            if self.app.get_ftrace_panel() is not None:
                self.app.get_ftrace_panel().append_data(parts[1])
        elif cmd == 'enable_kernel':
            self._app_window.get_menu().enable_kernel_menu()
        elif cmd == 'hook_java_callback':
            h = Hook(HOOK_JAVA)
            h.set_ptr(1)
            h.set_input(parts[1])
            if self.java_pending_args:
                h.set_condition(self.java_pending_args['condition'])
                h.set_logic(self.java_pending_args['logic'])
                self.java_pending_args = None
            self.java_hooks[h.get_input()] = h
            self.onAddJavaHook.emit(h)
        elif cmd == 'hook_java_on_load_callback':
            h = Hook(HOOK_JAVA)
            h.set_ptr(0)
            h.set_input(parts[1])
            self.java_on_loads[parts[1]] = h
            self.onAddJavaOnLoadHook.emit(h)
        elif cmd == 'hook_native_callback':
            h = Hook(HOOK_NATIVE)
            h.set_ptr(int(parts[1], 16))
            h.set_input(self.temporary_input)
            h.set_bytes(binascii.unhexlify(parts[2]))
            self.temporary_input = ''
            h.set_condition(parts[4])
            h.set_logic(parts[3])
            h.internalHook = parts[5] == 'true'
            h.set_debug_symbol(json.loads(parts[6]))
            self.native_pending_args = None
            if not h.internal_hook:
                self.hooks[h.get_ptr()] = h
                self.onAddNativeHook.emit(h)
        elif cmd == 'hook_native_on_load_callback':
            h = Hook(HOOK_ONLOAD)
            h.set_ptr(0)
            h.set_input(parts[1])
            self.native_on_loads[parts[1]] = h
            self.onAddNativeOnLoadHook.emit(h)
        elif cmd == 'hook_deleted':
            if parts[1] == 'java':
                self.java_hooks.pop(parts[2])
            elif parts[1] == 'native_on_load':
                self.native_on_loads.pop(parts[2])
            elif parts[1] == 'java_on_load':
                self.java_on_loads.pop(parts[2])
            else:
                self.hooks.pop(utils.parse_ptr(parts[2]))
            self.onDeleteHook.emit(parts)
        elif cmd == 'java_on_load_callback':
            str_fmt = ('Hook java onload {0} @thread := {1}'.format(parts[1], parts[2]))
            self.log_event(str_fmt)
            self.onHitJavaOnLoad.emit(parts[1])
        elif cmd == 'java_trace':
            self.onJavaTraceEvent.emit(parts)
        elif cmd == 'log':
            self.log(parts[1])
        elif cmd == 'native_on_load_callback':
            str_fmt = ('Hook native onload {0} @thread := {1}'.format(parts[1], parts[3]))
            self.log_event(str_fmt)
            self.onHitNativeOnLoad.emit([parts[1], parts[2]])
        elif cmd == 'native_on_load_module_loading':
            str_fmt = ('@thread {0} loading module := {1}'.format(parts[1], parts[2]))
            self.log_event(str_fmt)
        elif cmd == 'new_thread':
            str_fmt = ('@thread {0} starting new thread with target fn := {1}'.format(parts[1], parts[2]))
            self.log_event(str_fmt)
        elif cmd == 'release':
            str_fmt = ('releasing := {0}'.format(parts[1]))
            self.log_event(str_fmt)
            if parts[1] in self.contexts:
                del self.contexts[parts[1]]
            self.onThreadResumed.emit(int(parts[1]))
        elif cmd == 'resume':
            if not self.resumed:
                self.resume_proc()
        elif cmd == 'release_js':
            # releasing the thread must be done by calling py funct dwarf_api('release')
            # there are cases in which we want to release the thread from a js api so we need to call this
            self.onRequestJsThreadResume.emit(int(parts[1]))
        elif cmd == 'set_context':
            data = json.loads(parts[1])
            if 'modules' in data:
                self.onSetModules.emit(data['modules'])
            if 'ranges' in data:
                self.onSetRanges.emit(data['ranges'])
            if 'backtrace' in data:
                self.onBackTrace.emit(data['backtrace'])

            self.onApplyContext.emit(data)
        elif cmd == 'set_context_value':
            context_property = parts[1]
            value = parts[2]
            self.onContextChanged.emit(str(context_property), value)
        elif cmd == 'set_data':
            if data is not None:
                self.onSetData.emit(['raw', parts[1], data])
            else:
                self.onSetData.emit(['plain', parts[1], str(parts[2])])
        elif cmd == 'unhandled_exception':
            # todo
            pass
        elif cmd == 'update_modules':
            modules = json.loads(parts[2])
            # todo update onloads bases
            self.onSetModules.emit(modules)
        elif cmd == 'update_ranges':
            self.onSetRanges.emit(json.loads(parts[2]))
        elif cmd == 'watcher':
            exception = json.loads(parts[1])
            self.log_event('watcher hit op %s address %s @thread := %s' %
                     (exception['memory']['operation'], exception['memory']['address'], parts[2]))
        elif cmd == 'watcher_added':
            ptr = utils.parse_ptr(parts[1])
            hex_ptr = hex(ptr)
            flags = int(parts[2])

            h = Hook(HOOK_WATCHER)
            h.set_ptr(ptr)
            h.set_logic(flags)
            h.set_debug_symbol(json.loads(parts[3]))
            self.watchers[hex_ptr] = h

            self.onWatcherAdded.emit(hex_ptr, flags)
        elif cmd == 'watcher_removed':
            hex_ptr = hex(utils.parse_ptr(parts[1]))
            self.watchers.pop(hex_ptr)
            self.onWatcherRemoved.emit(hex_ptr)
        elif cmd == 'memoryscan_result':
            if parts[1] == '':
                self.onMemoryScanResult.emit([])
            else:
                self.onMemoryScanResult.emit(json.loads(parts[1]))
        else:
            print('unknown message: ' + what)
Пример #3
0
    def _on_message(self, message, data):
        QApplication.processEvents()
        if 'payload' not in message:
            print('payload: ' + str(message))
            return

        what = message['payload']
        parts = what.split(':::')
        if len(parts) < 2:
            print(what)
            return

        cmd = parts[0]
        if cmd == 'backtrace':
            try:
                self._app_window.backtrace_panel.set_backtrace(
                    json.loads(parts[1]))
            except:
                pass
        elif cmd == 'emulator':
            self.onEmulator.emit(parts[1:])
        elif cmd == 'enumerate_java_classes_start':
            self.onEnumerateJavaClassesStart.emit()
        elif cmd == 'enumerate_java_classes_match':
            self.onEnumerateJavaClassesMatch.emit(parts[1])
        elif cmd == 'enumerate_java_classes_complete':
            self.onEnumerateJavaClassesComplete.emit()
        elif cmd == 'enumerate_java_methods_complete':
            self.onEnumerateJavaMethodsComplete.emit(
                [parts[1], json.loads(parts[2])])
        elif cmd == 'ftrace':
            if self.app.get_ftrace_panel() is not None:
                self.app.get_ftrace_panel().append_data(parts[1])
        elif cmd == 'enable_kernel':
            self._app_window.get_menu().enable_kernel_menu()
        elif cmd == 'hook_java_callback':
            h = Hook(Hook.HOOK_JAVA)
            h.set_ptr(1)
            h.set_input(parts[1])
            if self.java_pending_args:
                h.set_condition(self.java_pending_args['condition'])
                h.set_logic(self.java_pending_args['logic'])
                self.java_pending_args = None
            self.java_hooks[h.get_input()] = h
            self.onAddJavaHook.emit(h)
        elif cmd == 'hook_native_callback':
            h = Hook(Hook.HOOK_NATIVE)
            h.set_ptr(int(parts[1], 16))
            h.set_input(self.temporary_input)
            h.set_bytes(binascii.unhexlify(parts[2]))
            self.temporary_input = ''
            h.set_condition(parts[4])
            h.set_logic(parts[3])
            self.native_pending_args = None
            self.hooks[h.get_ptr()] = h
            self.onAddNativeHook.emit(h)
        elif cmd == 'hook_onload_callback':
            h = Hook(Hook.HOOK_ONLOAD)
            h.set_ptr(0)
            h.set_input(parts[1])
            self.on_loads[parts[1]] = h
            self.onAddOnLoadHook.emit(h)
        elif cmd == 'java_trace':
            self.onJavaTraceEvent.emit(parts)
        elif cmd == 'log':
            self.log(parts[1])
        elif cmd == 'memory_scan_match':
            self.onMemoryScanMatch.emit(
                [parts[1], parts[2], json.loads(parts[3])])
        elif cmd == 'memory_scan_complete':
            self._app_window.get_menu().on_bytes_search_complete()
            self.onMemoryScanComplete.emit([parts[1] + ' complete', 0, 0])
        elif cmd == 'onload_callback':
            self.loading_library = parts[1]
            str_fmt = ('Hook onload {0} @thread := {1}'.format(
                parts[1], parts[3]))
            self.log(str_fmt)
            self.onHitOnLoad.emit([parts[1], parts[2]])
        elif cmd == 'release':
            if parts[1] in self.contexts:
                del self.contexts[parts[1]]
            self.onThreadResumed.emit(int(parts[1]))
        elif cmd == 'set_context':
            data = json.loads(parts[1])
            if 'modules' in data:
                self.onSetModules.emit(data['modules'])
            if 'ranges' in data:
                self.onSetRanges.emit(data['ranges'])

            self.onApplyContext.emit(data)
        elif cmd == 'set_data':
            if data:
                self.onSetData.emit(['raw', parts[1], data])
            else:
                self.onSetData.emit(['plain', parts[1], str(parts[2])])
        elif cmd == 'tracer':
            self.onTraceData.emit(parts[1])
        elif cmd == 'unhandled_exception':
            # todo
            pass
        elif cmd == 'update_modules':
            modules = json.loads(parts[2])
            # todo update onloads bases
            self.onSetModules.emit(modules)
        elif cmd == 'update_ranges':
            self.onSetRanges.emit(json.loads(parts[2]))
        elif cmd == 'watcher':
            exception = json.loads(parts[1])
            self.log('watcher hit op %s address %s @thread := %s' %
                     (exception['memory']['operation'],
                      exception['memory']['address'], parts[2]))
        elif cmd == 'watcher_added':
            self._watchers.append(utils.parse_ptr(parts[1]))
            self.onWatcherAdded.emit(parts[1], int(parts[2]))
        elif cmd == 'watcher_removed':
            self._watchers.remove(utils.parse_ptr(parts[1]))
            self.onWatcherRemoved.emit(parts[1])
        else:
            print('unknown message: ' + what)