mib created this revision. mib added reviewers: bulbazord, JDevlieghere. mib added a project: LLDB. Herald added a project: All. mib requested review of this revision. Herald added a subscriber: lldb-commits.
This patch changes the way we load a crash report into a scripted process by creating a empty target. To do so, it parses the architecture information from the report (for both the legacy and json format) and uses that to create a target that doesn't have any executable, like what we do when attaching to a process. For the legacy format, we mostly rely on the `Code Type` line, since the architure is an optional field on the `Binary Images` sections. However for the json format, we first try to get the architecture while parsing the image dictionary if we couldn't find it, we try to infer it using the "flavor" key when parsing the frame's registers. If the architecture is still not set after parsing the report, we use the host architecture, as a fallback. rdar://107850263 Signed-off-by: Med Ismail Bennani <ism...@bennani.ma> Repository: rG LLVM Github Monorepo https://reviews.llvm.org/D151849 Files: lldb/examples/python/crashlog.py lldb/source/Target/Process.cpp
Index: lldb/source/Target/Process.cpp =================================================================== --- lldb/source/Target/Process.cpp +++ lldb/source/Target/Process.cpp @@ -2515,7 +2515,7 @@ FileSpec exe_spec_to_use; if (!exe_module) { - if (!launch_info.GetExecutableFile()) { + if (!launch_info.GetExecutableFile() && !launch_info.IsScriptedProcess()) { error.SetErrorString("executable module does not exist"); return error; } Index: lldb/examples/python/crashlog.py =================================================================== --- lldb/examples/python/crashlog.py +++ lldb/examples/python/crashlog.py @@ -395,6 +395,10 @@ self.version = -1 self.target = None self.verbose = verbose + self.process_id = None + self.process_identifier = None + self.process_path = None + self.process_arch = None def dump(self): print("Crash Log File: %s" % (self.path)) @@ -484,9 +488,9 @@ def __init__(self, debugger, path, verbose): self.path = os.path.expanduser(path) self.verbose = verbose - self.crashlog = CrashLog(debugger, self.path, self.verbose) # List of DarwinImages sorted by their index. self.images = list() + self.crashlog = CrashLog(debugger, self.path, self.verbose) @abc.abstractmethod def parse(self): @@ -547,6 +551,8 @@ def parse_process_info(self, json_data): self.crashlog.process_id = json_data["pid"] self.crashlog.process_identifier = json_data["procName"] + if "procPath" in json_data: + self.crashlog.process_path = json_data["procPath"] def parse_crash_reason(self, json_exception): self.crashlog.exception = json_exception @@ -574,6 +580,10 @@ darwin_image = self.crashlog.DarwinImage( low, high, name, version, img_uuid, path, self.verbose ) + if "arch" in json_image: + darwin_image.arch = json_image["arch"] + if path == self.crashlog.process_path: + self.crashlog.process_arch = darwin_image.arch self.images.append(darwin_image) self.crashlog.images.append(darwin_image) @@ -740,6 +750,13 @@ gpr_dict = {str(idx): reg for idx, reg in enumerate(state)} registers.update(self.parse_thread_registers(gpr_dict, key)) continue + if key == "flavor": + if not self.crashlog.process_arch: + if state == "ARM_THREAD_STATE64": + self.crashlog.process_arch = "arm64" + elif state == "X86_THREAD_STATE": + self.crashlog.process_arch = "x86_64" + continue try: value = int(state["value"]) registers["{}{}".format(prefix or "", key)] = value @@ -912,6 +929,8 @@ line[8:].strip().split(" [") ) self.crashlog.process_id = pid_with_brackets.strip("[]") + elif line.startswith("Path:"): + self.crashlog.process_path = line[5:].strip() elif line.startswith("Identifier:"): self.crashlog.process_identifier = line[11:].strip() elif line.startswith("Version:"): @@ -923,6 +942,11 @@ else: self.crashlog.process = version_string self.crashlog.process_compatability_version = version_string + elif line.startswith("Code Type:"): + if "ARM-64" in line: + self.crashlog.process_arch = "arm64" + elif "X86-64" in line: + self.crashlog.process_arch = "x86_64" elif self.parent_process_regex.search(line): parent_process_match = self.parent_process_regex.search(line) self.crashlog.parent_process_name = parent_process_match.group(1) @@ -1343,9 +1367,12 @@ # 2. If the user didn't provide a target, try to create a target using the symbolicator if not target or not target.IsValid(): target = crashlog.create_target() - # 3. If that didn't work, and a target is already loaded, use it - if (target is None or not target.IsValid()) and debugger.GetNumTargets() > 0: - target = debugger.GetTargetAtIndex(0) + # 3. If that didn't work, create a dummy target + if target is None or not target.IsValid(): + arch = crashlog.process_arch + if not arch: + arch = platform.machine() + target = debugger.CreateTargetWithFileAndArch(None, arch) # 4. Fail if target is None or not target.IsValid(): raise InteractiveCrashLogException("couldn't create target")
_______________________________________________ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits