def writeWord(self, address, word): """ Address have to be aligned! """ debug("Write word %s at %s" % ( formatWordHex(word), formatAddress(address))) ptrace_poketext(self.pid, address, word)
def writeWord(self, address, word): """ Address have to be aligned! """ debug("Write word %s at %s" % (formatWordHex(word), formatAddress(address))) ptrace_poketext(self.pid, address, word)
def setreg(self, name, value): debug("Set register %s to %s" % (name, formatWordHex(value))) if name not in REGISTER_NAMES: raise ProcessError(self, "Unknown register: %r" % name) regs = self.getregs() setattr(regs, name, value) self.setregs(regs)
def exit(self): if self.name in PREFORMAT_ARGUMENTS: preformat = set(PREFORMAT_ARGUMENTS[self.name]) else: preformat = set() # Data pointed by arguments may have changed during the syscall # e.g. uname() syscall for index, argument in enumerate(self.arguments): if index in preformat: # Don't lose preformatted arguments continue if argument.type and not argument.type.endswith("*"): continue argument.text = None self.result = self.process.getreg(RETURN_VALUE_REGISTER) if self.restype.endswith("*"): text = formatAddress(self.result) else: uresult = self.result self.result = ulong2long(self.result) if self.result < 0 and (-self.result) in errorcode: errcode = -self.result text = "%s %s (%s)" % ( self.result, errorcode[errcode], strerror(errcode)) elif not(0 <= self.result <= 9): text = "%s (%s)" % (self.result, formatWordHex(uresult)) else: text = str(self.result) self.result_text = text return text
def exit(self): if self.name in PREFORMAT_ARGUMENTS: preformat = set(PREFORMAT_ARGUMENTS[self.name]) else: preformat = set() # Data pointed by arguments may have changed during the syscall # eg. uname() syscall for index, argument in enumerate(self.arguments): if index in preformat: # Don't lose preformatted arguments continue if argument.type and not argument.type.endswith("*"): continue argument.text = None self.result = self.process.getreg(RETURN_VALUE_REGISTER) if self.restype.endswith("*"): text = formatAddress(self.result) else: uresult = self.result self.result = ulong2long(self.result) if self.result < 0: text = "%s %s (%s)" % ( self.result, errorcode[-self.result], strerror(-self.result)) elif not(0 <= self.result <= 9): text = "%s (%s)" % (self.result, formatWordHex(uresult)) else: text = str(self.result) self.result_text = text return text
def createText(self): value = self.value argtype = self.type name = self.name if not argtype or not name: return formatWordHex(self.value) syscall = self.function.name # Special cases try: return SYSCALL_ARG_DICT[syscall][name][value] except KeyError: pass try: callback = ARGUMENT_CALLBACK[syscall][name] except KeyError: callback = None if callback: return callback(value) if syscall == "execve": if name in ("argv", "envp"): return self.readCStringArray(value) if syscall == "socketcall": if name == "call": try: return SOCKETCALL[value][0] except KeyError: return str(value) if name == "args": func_call = FunctionCall("socketcall", self.options) setupSocketCall(func_call, self.function.process, self.function[0], self.value) text = "<%s>" % func_call.format() return self.formatPointer(text, self.value) if syscall == "write" and name == "buf": fd = self.function[0].value if fd < 3: length = self.function[2].value return self.readString(value, length) if name == "signum": return signalName(value) if name in FILENAME_ARGUMENTS: return self.readCString(value) # Remove "const " prefix if argtype.startswith("const "): argtype = argtype[6:] # Format depending on the type if argtype.endswith("*"): try: text = self.formatValuePointer(argtype[:-1]) if text: return text except PTRACE_ERRORS, err: writeError(getLogger(), err, "Format argument value error") value = None return formatAddress(self.value)
def display(self, log): log(self.text) self.displayExtra(log) if self.instr: log("- instruction: %s" % self.instr) for mapping in self.mappings: log("- mapping: %s" % mapping) for name, value in self.registers.items(): log("- register %s=%s" % (name, formatWordHex(value)))
def print_(self, command): try: value = self.parseInteger(command) except ValueError as err: return str(err) error("Decimal: %s" % value) error("Hexadecimal: %s" % formatWordHex(value)) for map in self.process.readMappings(): if value not in map: continue error("Address is part of mapping: %s" % map) return None
def dumpRegs(log, regs): width = max( len(name) for name, type in regs._fields_ ) name_format = "%% %us" % width for name, type in regs._fields_: value = getattr(regs, name) name = name_format % name if sizeof(type) == 32: value = formatUintHex32(value) elif sizeof(type) == 16: value = formatUintHex16(value) else: value = formatWordHex(value) log("%s = %s" % (name, value))
def dumpRegs(log, regs): width = max(len(name) for name, type in regs._fields_) name_format = "%% %us" % width for name, type in regs._fields_: value = getattr(regs, name) name = name_format % name if sizeof(type) == 32: value = formatUintHex32(value) elif sizeof(type) == 16: value = formatUintHex16(value) else: value = formatWordHex(value) log("%s = %s" % (name, value))
def _dumpStack(self): sp = self.getStackPointer() displayed = 0 for index in xrange(-5, 5 + 1): delta = index * CPU_WORD_SIZE try: value = self.readWord(sp + delta) error("STACK%+ 3i: %s" % (delta, formatWordHex(value))) displayed += 1 except PtraceError: pass if not displayed: error("ERROR: unable to read stack (%s)" % formatAddress(sp))
def _dumpStack(self, log): sp = self.getStackPointer() displayed = 0 for index in range(-5, 5 + 1): delta = index * CPU_WORD_SIZE try: value = self.readWord(sp + delta) log("STACK%+ 3i: %s" % (delta, formatWordHex(value))) displayed += 1 except PtraceError: pass if not displayed: log("ERROR: unable to read the stack (SP=%s)" % formatAddress(sp))
def dumpRegs(log, regs): """ Dump all registers using log callback (write one line). """ width = max( len(name) for name, type in regs._fields_ ) name_format = "%% %us" % width for name, type in regs._fields_: value = getattr(regs, name) name = name_format % name if sizeof(type) == 32: value = formatUintHex32(value) elif sizeof(type) == 16: value = formatUintHex16(value) else: value = formatWordHex(value) log("%s = %s" % (name, value))
def exit(self): if self.name in PREFORMAT_ARGUMENTS: preformat = set(PREFORMAT_ARGUMENTS[self.name]) else: preformat = set() # Data pointed by arguments may have changed during the syscall # eg. uname() syscall for index, argument in enumerate(self.arguments): if index in preformat: # Don't lose preformatted arguments continue if argument.type and not argument.type.endswith("*"): continue argument.text = None if CPU_ARM: regname = "r0" elif CPU_I386: regname = "eax" elif CPU_X86_64: regname = "rax" elif CPU_POWERPC: regname = "result" else: raise NotImplementedError() self.result = self.process.getreg(regname) if self.restype.endswith("*"): text = formatAddress(self.result) else: uresult = self.result self.result = ulong2long(self.result) if self.result < 0: text = "%s (%s)" % ( self.result, strerror(-self.result)) elif not(0 <= self.result <= 9): text = "%s (%s)" % (self.result, formatWordHex(uresult)) else: text = str(self.result) self.result_text = text return text
def exit(self): if self.name in PREFORMAT_ARGUMENTS: preformat = set(PREFORMAT_ARGUMENTS[self.name]) else: preformat = set() # Data pointed by arguments may have changed during the syscall # eg. uname() syscall for index, argument in enumerate(self.arguments): if index in preformat: # Don't lose preformatted arguments continue if argument.type and not argument.type.endswith("*"): continue argument.text = None if CPU_I386: regname = "eax" elif CPU_X86_64: regname = "rax" elif CPU_POWERPC: regname = "result" else: raise NotImplementedError() self.result = self.process.getreg(regname) if self.restype.endswith("*"): text = formatAddress(self.result) else: uresult = self.result self.result = ulong2long(self.result) if self.result < 0: text = "%s (%s)" % (self.result, strerror(-self.result)) elif not (0 <= self.result <= 9): text = "%s (%s)" % (self.result, formatWordHex(uresult)) else: text = str(self.result) self.result_text = text return text
def formatExit(self, process): if CPU_I386: regname = "eax" elif CPU_X86_64: regname = "rax" elif CPU_PPC: regname = "result" else: raise NotImplementedError() self.result = process.getreg(regname) if self.restype.endswith("*"): text = formatAddress(self.result) else: uresult = self.result self.result = ulong2long(self.result) if self.result < 0: text = "%s (%s)" % (self.result, strerror(-self.result)) elif not (0 <= self.result <= 9): text = "%s (%s)" % (self.result, formatWordHex(uresult)) else: text = str(self.result) return text
def formatExit(self, process): if CPU_I386: regname = "eax" elif CPU_X86_64: regname = "rax" elif CPU_PPC: regname = "result" else: raise NotImplementedError() self.result = process.getreg(regname) if self.restype.endswith("*"): text = formatAddress(self.result) else: uresult = self.result self.result = ulong2long(self.result) if self.result < 0: text = "%s (%s)" % ( self.result, strerror(-self.result)) elif not(0 <= self.result <= 9): text = "%s (%s)" % (self.result, formatWordHex(uresult)) else: text = str(self.result) return text
def readWord(self, address): """Address have to be aligned!""" word = ptrace_peektext(self.pid, address) debug("Read word at %s: %s" % (formatAddress(address), formatWordHex(word))) return word
def createText(self): value = self.value argtype = self.type name = self.name if not argtype or not name: return formatWordHex(self.value) syscall = self.function.name # Special cases try: return SYSCALL_ARG_DICT[syscall][name][value] except KeyError: pass try: callback = ARGUMENT_CALLBACK[syscall][name] except KeyError: callback = None if callback: return callback(self) if syscall == "execve": if name in ("argv", "envp"): return self.readCStringArray(value) if syscall == "socketcall": if name == "call": try: return SOCKETCALL[value] except KeyError: return str(value) if name == "args": func_call = FunctionCall("socketcall", self.options) setupSocketCall(func_call, self.function.process, self.function[0], self.value) text = "<%s>" % func_call.format() return self.formatPointer(text, self.value) if syscall == "write" and name == "buf": fd = self.function[0].value if fd < 3: length = self.function[2].value return self.readString(value, length) if name == "signum": return signalName(value) if name in DIRFD_ARGUMENTS and argtype == "int": return formatDirFd(uint2int(value)) # Remove "const " prefix if argtype.startswith("const "): argtype = argtype[6:] if name in FILENAME_ARGUMENTS and argtype == "char *": return self.readCString(value) # Format depending on the type if argtype.endswith("*"): try: text = self.formatValuePointer(argtype[:-1]) if text: return text except PTRACE_ERRORS as err: writeError(getLogger(), err, "Warning: Format %r value error" % self, log_level=INFO) return formatAddress(self.value) # Array like "int[2]" match = re.match("(.*)\[([0-9])+\]", argtype) if match: basetype = match.group(1) count = int(match.group(2)) if basetype == "int": return self.readArray(self.value, c_int, count) # Simple types if argtype in ("unsigned int", "unsigned long", "u32"): return str(self.value) if argtype in INTEGER_TYPES: return str(uint2int(self.value)) # Default formatter: hexadecimal return formatWordHex(self.value)
def __str__(self): arguments = (formatWordHex(arg) for arg in self.arguments) return u"IP=%s: %s (%s)" % (formatAddress(self.ip), self.name, ", ".join(arguments))
def readWord(self, address): """Address have to be aligned!""" word = ptrace_peektext(self.pid, address) debug("Read word at %s: %s" % ( formatAddress(address), formatWordHex(word))) return word