[Lldb-commits] [lldb] ebf2490 - [lldb] SBTarget::AddModule do all searches by UUID, set Target arch

Jason Molenda via lldb-commits lldb-commits at lists.llvm.org
Fri Aug 11 14:20:44 PDT 2023


Author: Jason Molenda
Date: 2023-08-11T14:20:38-07:00
New Revision: ebf249066ac5c7917064eb56a9e51c21000cdf93

URL: https://github.com/llvm/llvm-project/commit/ebf249066ac5c7917064eb56a9e51c21000cdf93
DIFF: https://github.com/llvm/llvm-project/commit/ebf249066ac5c7917064eb56a9e51c21000cdf93.diff

LOG: [lldb] SBTarget::AddModule do all searches by UUID, set Target arch

Make SBTarget::AddModule possibly call out to an external program to
find the binary by UUID if it can't be found more easily, the same
way `target modules add -u ...` works from the commandline.

If the Target does not have an architecture set yet, use the
Module's Arch to initialize it.  Allows an API writer to create
a target with no arch, and inherit it from the first binary they
load with AddModules.

Differential Revision: https://reviews.llvm.org/D157659
rdar://113657555

Added: 
    lldb/test/API/python_api/target-arch-from-module/Makefile
    lldb/test/API/python_api/target-arch-from-module/TestTargetArchFromModule.py
    lldb/test/API/python_api/target-arch-from-module/main.c

Modified: 
    lldb/source/API/SBTarget.cpp

Removed: 
    


################################################################################
diff  --git a/lldb/source/API/SBTarget.cpp b/lldb/source/API/SBTarget.cpp
index 3fef7428abe24b..e38edf8e44652e 100644
--- a/lldb/source/API/SBTarget.cpp
+++ b/lldb/source/API/SBTarget.cpp
@@ -7,6 +7,7 @@
 //===----------------------------------------------------------------------===//
 
 #include "lldb/API/SBTarget.h"
+#include "lldb/Symbol/LocateSymbolFile.h"
 #include "lldb/Utility/Instrumentation.h"
 #include "lldb/Utility/LLDBLog.h"
 #include "lldb/lldb-public.h"
@@ -1477,28 +1478,29 @@ lldb::SBModule SBTarget::AddModule(const char *path, const char *triple,
                                    const char *uuid_cstr, const char *symfile) {
   LLDB_INSTRUMENT_VA(this, path, triple, uuid_cstr, symfile);
 
-  lldb::SBModule sb_module;
   TargetSP target_sp(GetSP());
-  if (target_sp) {
-    ModuleSpec module_spec;
-    if (path)
-      module_spec.GetFileSpec().SetFile(path, FileSpec::Style::native);
+  if (!target_sp)
+    return {};
 
-    if (uuid_cstr)
-      module_spec.GetUUID().SetFromStringRef(uuid_cstr);
+  ModuleSpec module_spec;
+  if (path)
+    module_spec.GetFileSpec().SetFile(path, FileSpec::Style::native);
 
-    if (triple)
-      module_spec.GetArchitecture() = Platform::GetAugmentedArchSpec(
-          target_sp->GetPlatform().get(), triple);
-    else
-      module_spec.GetArchitecture() = target_sp->GetArchitecture();
+  if (uuid_cstr)
+    module_spec.GetUUID().SetFromStringRef(uuid_cstr);
 
-    if (symfile)
-      module_spec.GetSymbolFileSpec().SetFile(symfile, FileSpec::Style::native);
+  if (triple)
+    module_spec.GetArchitecture() =
+        Platform::GetAugmentedArchSpec(target_sp->GetPlatform().get(), triple);
+  else
+    module_spec.GetArchitecture() = target_sp->GetArchitecture();
 
-    sb_module.SetSP(target_sp->GetOrCreateModule(module_spec, true /* notify */));
-  }
-  return sb_module;
+  if (symfile)
+    module_spec.GetSymbolFileSpec().SetFile(symfile, FileSpec::Style::native);
+
+  SBModuleSpec sb_modulespec(module_spec);
+
+  return AddModule(sb_modulespec);
 }
 
 lldb::SBModule SBTarget::AddModule(const SBModuleSpec &module_spec) {
@@ -1506,9 +1508,26 @@ lldb::SBModule SBTarget::AddModule(const SBModuleSpec &module_spec) {
 
   lldb::SBModule sb_module;
   TargetSP target_sp(GetSP());
-  if (target_sp)
+  if (target_sp) {
     sb_module.SetSP(target_sp->GetOrCreateModule(*module_spec.m_opaque_up,
                                                  true /* notify */));
+    if (!sb_module.IsValid() && module_spec.m_opaque_up->GetUUID().IsValid()) {
+      Status error;
+      if (Symbols::DownloadObjectAndSymbolFile(*module_spec.m_opaque_up, error,
+                                               /* force_lookup */ true)) {
+        if (FileSystem::Instance().Exists(
+                module_spec.m_opaque_up->GetFileSpec())) {
+          sb_module.SetSP(target_sp->GetOrCreateModule(*module_spec.m_opaque_up,
+                                                       true /* notify */));
+        }
+      }
+    }
+  }
+  // If the target hasn't initialized any architecture yet, use the
+  // binary's architecture.
+  if (sb_module.IsValid() && !target_sp->GetArchitecture().IsValid() &&
+      sb_module.GetSP()->GetArchitecture().IsValid())
+    target_sp->SetArchitecture(sb_module.GetSP()->GetArchitecture());
   return sb_module;
 }
 

diff  --git a/lldb/test/API/python_api/target-arch-from-module/Makefile b/lldb/test/API/python_api/target-arch-from-module/Makefile
new file mode 100644
index 00000000000000..10495940055b63
--- /dev/null
+++ b/lldb/test/API/python_api/target-arch-from-module/Makefile
@@ -0,0 +1,3 @@
+C_SOURCES := main.c
+
+include Makefile.rules

diff  --git a/lldb/test/API/python_api/target-arch-from-module/TestTargetArchFromModule.py b/lldb/test/API/python_api/target-arch-from-module/TestTargetArchFromModule.py
new file mode 100644
index 00000000000000..260f37c9ed2300
--- /dev/null
+++ b/lldb/test/API/python_api/target-arch-from-module/TestTargetArchFromModule.py
@@ -0,0 +1,107 @@
+"""
+An SBTarget with no arch, call AddModule, SBTarget's arch should be set.
+"""
+
+import os
+import subprocess
+import re
+import lldb
+from lldbsuite.test.decorators import *
+from lldbsuite.test.lldbtest import *
+from lldbsuite.test import lldbutil
+
+
+class TargetArchFromModule(TestBase):
+    @skipIf(
+        debug_info=no_match(["dsym"]),
+        bugnumber="This test is looking explicitly for a dSYM",
+    )
+    @skipUnlessDarwin
+    @skipIfRemote
+    def test_target_arch_init(self):
+        self.build()
+        aout_exe = self.getBuildArtifact("a.out")
+        aout_dsym = self.getBuildArtifact("a.out.dSYM")
+        hidden_dir = self.getBuildArtifact("hide.noindex")
+        hidden_aout_exe = self.getBuildArtifact("hide.noindex/a.out")
+        hidden_aout_dsym = self.getBuildArtifact("hide.noindex/a.out.dSYM")
+        dsym_for_uuid = self.getBuildArtifact("dsym-for-uuid.sh")
+
+        # We can hook in our dsym-for-uuid shell script to lldb with
+        # this env var instead of requiring a defaults write.
+        os.environ["LLDB_APPLE_DSYMFORUUID_EXECUTABLE"] = dsym_for_uuid
+        self.addTearDownHook(
+            lambda: os.environ.pop("LLDB_APPLE_DSYMFORUUID_EXECUTABLE", None)
+        )
+
+        dwarfdump_uuid_regex = re.compile("UUID: ([-0-9a-fA-F]+) \(([^\(]+)\) .*")
+        dwarfdump_cmd_output = subprocess.check_output(
+            ('/usr/bin/dwarfdump --uuid "%s"' % aout_exe), shell=True
+        ).decode("utf-8")
+        aout_uuid = None
+        for line in dwarfdump_cmd_output.splitlines():
+            match = dwarfdump_uuid_regex.search(line)
+            if match:
+                aout_uuid = match.group(1)
+        self.assertNotEqual(aout_uuid, None, "Could not get uuid of built a.out")
+
+        ###  Create our dsym-for-uuid shell script which returns self.hidden_aout_exe.
+        shell_cmds = [
+            "#! /bin/sh",
+            "# the last argument is the uuid",
+            "while [ $# -gt 1 ]",
+            "do",
+            "  shift",
+            "done",
+            "ret=0",
+            'echo "<?xml version=\\"1.0\\" encoding=\\"UTF-8\\"?>"',
+            'echo "<!DOCTYPE plist PUBLIC \\"-//Apple//DTD PLIST 1.0//EN\\" \\"http://www.apple.com/DTDs/PropertyList-1.0.dtd\\">"',
+            'echo "<plist version=\\"1.0\\">"',
+            "",
+            'if [ "$1" = "%s" ]' % aout_uuid,
+            "then",
+            "  uuid=%s" % aout_uuid,
+            "  bin=%s" % hidden_aout_exe,
+            "  dsym=%s.dSYM/Contents/Resources/DWARF/%s"
+            % (hidden_aout_exe, os.path.basename(hidden_aout_exe)),
+            "fi",
+            'echo "  <dict>"',
+            'echo "    <key>$1</key>"',
+            'echo "    <dict>"',
+            'if [ -z "$uuid" -o -z "$bin" -o ! -f "$bin" ]',
+            "then",
+            '  echo "      <key>DBGError</key>"',
+            '  echo "      <string>not found by $0</string>"',
+            '  echo "    </dict>"',
+            '  echo "  </dict>"',
+            '  echo "</plist>"',
+            "  exit 0",
+            "fi",
+            "",
+            'echo "<key>DBGDSYMPath</key><string>$dsym</string>"',
+            'echo "<key>DBGSymbolRichExecutable</key><string>$bin</string>"',
+            'echo "</dict></dict></plist>"',
+            "exit $ret",
+        ]
+
+        with open(dsym_for_uuid, "w") as writer:
+            for l in shell_cmds:
+                writer.write(l + "\n")
+
+        os.chmod(dsym_for_uuid, 0o755)
+
+        # Move the main binary and its dSYM into the hide.noindex
+        # directory.  Now the only way lldb can find them is with
+        # the LLDB_APPLE_DSYMFORUUID_EXECUTABLE shell script -
+        # so we're testing that this dSYM discovery method works.
+        lldbutil.mkdir_p(hidden_dir)
+        os.rename(aout_exe, hidden_aout_exe)
+        os.rename(aout_dsym, hidden_aout_dsym)
+
+        target = self.dbg.CreateTarget("")
+        self.assertTrue(target.IsValid())
+        self.expect("target list", matching=False, substrs=["arch="])
+
+        m = target.AddModule(None, None, aout_uuid)
+        self.assertTrue(m.IsValid())
+        self.expect("target list", substrs=["arch="])

diff  --git a/lldb/test/API/python_api/target-arch-from-module/main.c b/lldb/test/API/python_api/target-arch-from-module/main.c
new file mode 100644
index 00000000000000..ab597e7dc6b2e8
--- /dev/null
+++ b/lldb/test/API/python_api/target-arch-from-module/main.c
@@ -0,0 +1,5 @@
+#include <stdio.h>
+int main() {
+  puts("HI i am a program");
+  return 0;
+}


        


More information about the lldb-commits mailing list