[lldb] Add an overload to SetModuleLoadAddress that takes an unsigned value
authorJonas Devlieghere <jonas@devlieghere.com>
Thu, 6 Apr 2023 17:27:06 +0000 (10:27 -0700)
committerJonas Devlieghere <jonas@devlieghere.com>
Thu, 6 Apr 2023 17:43:54 +0000 (10:43 -0700)
Currently, SBTarget::SetModuleLoadAddress does not accept large slides
needed to load images in high memory. This function should always have
taken an unsigned as the slide, as it immediately passes it to
Target::SetSectionLoadAddress which takes an unsigned.

This patch adds an overload and exposes that to SWIG instead of the
signed variant. I've marked the signed variant as deprecated and added
check that the slide is positive.

rdar://101355155

Differential revision: https://reviews.llvm.org/D147482

lldb/include/lldb/API/SBTarget.h
lldb/source/API/SBTarget.cpp
lldb/test/API/functionalities/multiple-slides/TestMultipleSlides.py

index 072cf31..404e905 100644 (file)
@@ -371,6 +371,7 @@ public:
   ///     failure.
   lldb::SBError ClearSectionLoadAddress(lldb::SBSection section);
 
+#ifndef SWIG
   /// Slide all file addresses for all module sections so that \a module
   /// appears to loaded at these slide addresses.
   ///
@@ -389,8 +390,31 @@ public:
   /// \return
   ///     An error to indicate success, fail, and any reason for
   ///     failure.
+  [[deprecated("Use SetModuleLoadAddress(lldb::SBModule, uint64_t)")]]
   lldb::SBError SetModuleLoadAddress(lldb::SBModule module,
                                      int64_t sections_offset);
+#endif
+
+  /// Slide all file addresses for all module sections so that \a module
+  /// appears to loaded at these slide addresses.
+  ///
+  /// When you need all sections within a module to be loaded at a
+  /// rigid slide from the addresses found in the module object file,
+  /// this function will allow you to easily and quickly slide all
+  /// module sections.
+  ///
+  /// \param[in] module
+  ///     The module to load.
+  ///
+  /// \param[in] sections_offset
+  ///     An offset that will be applied to all section file addresses
+  ///     (the virtual addresses found in the object file itself).
+  ///
+  /// \return
+  ///     An error to indicate success, fail, and any reason for
+  ///     failure.
+  lldb::SBError SetModuleLoadAddress(lldb::SBModule module,
+                                     uint64_t sections_offset);
 
   /// Clear the section base load addresses for all sections in a module.
   ///
index ddde1ba..301602c 100644 (file)
@@ -2093,6 +2093,18 @@ SBError SBTarget::SetModuleLoadAddress(lldb::SBModule module,
                                        int64_t slide_offset) {
   LLDB_INSTRUMENT_VA(this, module, slide_offset);
 
+  if (slide_offset < 0) {
+    SBError sb_error;
+    sb_error.SetErrorStringWithFormat("slide must be positive");
+    return sb_error;
+  }
+
+  return SetModuleLoadAddress(module, static_cast<uint64_t>(slide_offset));
+}
+
+SBError SBTarget::SetModuleLoadAddress(lldb::SBModule module,
+                                               uint64_t slide_offset) {
+
   SBError sb_error;
 
   TargetSP target_sp(GetSP());
index c54c401..2a2e795 100644 (file)
@@ -36,14 +36,14 @@ class MultipleSlidesTestCase(TestBase):
         self.assertEqual(first_sym.GetStartAddress().GetLoadAddress(target), lldb.LLDB_INVALID_ADDRESS)
         self.assertEqual(second_sym.GetStartAddress().GetLoadAddress(target), lldb.LLDB_INVALID_ADDRESS)
 
-
         # View the first element of `first` and `second` with
         # no slide applied, but with load address set.
         #
         # In memory, we have something like
         #    0x1000 - 0x17ff  first[]
         #    0x1800 - 0x1fff  second[]
-        target.SetModuleLoadAddress(module, 0)
+        error = target.SetModuleLoadAddress(module, 0)
+        self.assertSuccess(error)
         self.expect("expression/d ((int*)&first)[0]", substrs=['= 5'])
         self.expect("expression/d ((int*)&second)[0]", substrs=['= 6'])
         self.assertEqual(first_sym.GetStartAddress().GetLoadAddress(target), 
@@ -60,7 +60,8 @@ class MultipleSlidesTestCase(TestBase):
         # but if the original entries are still present in lldb, 
         # the beginning address of second[] will get a load address
         # of 0x1800, instead of 0x17c0 (0x1800-64) as we need to get.
-        target.SetModuleLoadAddress(module, first_size - 64)
+        error = target.SetModuleLoadAddress(module, first_size - 64)
+        self.assertSuccess(error)
         self.expect("expression/d ((int*)&first)[0]", substrs=['= 5'])
         self.expect("expression/d ((int*)&second)[0]", substrs=['= 6'])
         self.assertNotEqual(first_sym.GetStartAddress().GetLoadAddress(target), 
@@ -69,7 +70,8 @@ class MultipleSlidesTestCase(TestBase):
                          second_sym.GetStartAddress().GetFileAddress())
 
         # Slide it back to the original vmaddr.
-        target.SetModuleLoadAddress(module, 0)
+        error = target.SetModuleLoadAddress(module, 0)
+        self.assertSuccess(error)
         self.expect("expression/d ((int*)&first)[0]", substrs=['= 5'])
         self.expect("expression/d ((int*)&second)[0]", substrs=['= 6'])
         self.assertEqual(first_sym.GetStartAddress().GetLoadAddress(target), 
@@ -77,3 +79,6 @@ class MultipleSlidesTestCase(TestBase):
         self.assertEqual(second_sym.GetStartAddress().GetLoadAddress(target),
                          second_sym.GetStartAddress().GetFileAddress())
 
+        # Make sure we can use a slide > INT64_MAX.
+        error = target.SetModuleLoadAddress(module, 0xffffffff12345678)
+        self.assertSuccess(error)