asmith updated this revision to Diff 186796.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D56237/new/

https://reviews.llvm.org/D56237

Files:
  source/Plugins/DynamicLoader/Windows-DYLD/DynamicLoaderWindowsDYLD.cpp
  source/Plugins/DynamicLoader/Windows-DYLD/DynamicLoaderWindowsDYLD.h
  source/Plugins/Process/Windows/Common/ProcessWindows.cpp
  source/Plugins/Process/Windows/Common/ProcessWindows.h

Index: source/Plugins/Process/Windows/Common/ProcessWindows.h
===================================================================
--- source/Plugins/Process/Windows/Common/ProcessWindows.h
+++ source/Plugins/Process/Windows/Common/ProcessWindows.h
@@ -16,6 +16,7 @@
 #include "llvm/Support/Mutex.h"
 
 #include "IDebugDelegate.h"
+#include "Plugins/DynamicLoader/Windows-DYLD/DynamicLoaderWindowsDYLD.h"
 
 namespace lldb_private {
 
@@ -90,6 +91,8 @@
 
   lldb::addr_t GetImageInfoAddress() override;
 
+  DynamicLoaderWindowsDYLD *GetDynamicLoader();
+
   // IDebugDelegate overrides.
   void OnExitProcess(uint32_t exit_code) override;
   void OnDebuggerConnected(lldb::addr_t image_base) override;
Index: source/Plugins/Process/Windows/Common/ProcessWindows.cpp
===================================================================
--- source/Plugins/Process/Windows/Common/ProcessWindows.cpp
+++ source/Plugins/Process/Windows/Common/ProcessWindows.cpp
@@ -864,6 +864,13 @@
     return LLDB_INVALID_ADDRESS;
 }
 
+DynamicLoaderWindowsDYLD *ProcessWindows::GetDynamicLoader() {
+  if (m_dyld_ap.get() == NULL)
+    m_dyld_ap.reset(DynamicLoader::FindPlugin(
+        this, DynamicLoaderWindowsDYLD::GetPluginNameStatic().GetCString()));
+  return static_cast<DynamicLoaderWindowsDYLD *>(m_dyld_ap.get());
+}
+
 void ProcessWindows::OnExitProcess(uint32_t exit_code) {
   // No need to acquire the lock since m_session_data isn't accessed.
   Log *log = ProcessWindowsLog::GetLogIfAny(WINDOWS_LOG_PROCESS);
@@ -916,12 +923,10 @@
     GetTarget().SetExecutableModule(module, eLoadDependentsNo);
   }
 
-  bool load_addr_changed;
-  module->SetLoadAddress(GetTarget(), image_base, false, load_addr_changed);
-
-  ModuleList loaded_modules;
-  loaded_modules.Append(module);
-  GetTarget().ModulesDidLoad(loaded_modules);
+  if (auto dyld = GetDynamicLoader())
+    dyld->OnLoadModule(
+        ModuleSpec(module->GetFileSpec(), module->GetArchitecture()),
+        image_base);
 
   // Add the main executable module to the list of pending module loads.  We
   // can't call GetTarget().ModulesDidLoad() here because we still haven't
@@ -1027,29 +1032,13 @@
 
 void ProcessWindows::OnLoadDll(const ModuleSpec &module_spec,
                                lldb::addr_t module_addr) {
-  // Confusingly, there is no Target::AddSharedModule.  Instead, calling
-  // GetSharedModule() with a new module will add it to the module list and
-  // return a corresponding ModuleSP.
-  Status error;
-  ModuleSP module = GetTarget().GetSharedModule(module_spec, &error);
-  bool load_addr_changed = false;
-  module->SetLoadAddress(GetTarget(), module_addr, false, load_addr_changed);
-
-  ModuleList loaded_modules;
-  loaded_modules.Append(module);
-  GetTarget().ModulesDidLoad(loaded_modules);
+  if (auto dyld = GetDynamicLoader())
+    dyld->OnLoadModule(module_spec, module_addr);
 }
 
 void ProcessWindows::OnUnloadDll(lldb::addr_t module_addr) {
-  Address resolved_addr;
-  if (GetTarget().ResolveLoadAddress(module_addr, resolved_addr)) {
-    ModuleSP module = resolved_addr.GetModule();
-    if (module) {
-      ModuleList unloaded_modules;
-      unloaded_modules.Append(module);
-      GetTarget().ModulesDidUnload(unloaded_modules, false);
-    }
-  }
+  if (auto dyld = GetDynamicLoader())
+    dyld->OnUnloadModule(module_addr);
 }
 
 void ProcessWindows::OnDebugString(const std::string &string) {}
Index: source/Plugins/DynamicLoader/Windows-DYLD/DynamicLoaderWindowsDYLD.h
===================================================================
--- source/Plugins/DynamicLoader/Windows-DYLD/DynamicLoaderWindowsDYLD.h
+++ source/Plugins/DynamicLoader/Windows-DYLD/DynamicLoaderWindowsDYLD.h
@@ -12,6 +12,8 @@
 #include "lldb/Target/DynamicLoader.h"
 #include "lldb/lldb-forward.h"
 
+#include <map>
+
 namespace lldb_private {
 
 class DynamicLoaderWindowsDYLD : public DynamicLoader {
@@ -27,6 +29,9 @@
 
   static DynamicLoader *CreateInstance(Process *process, bool force);
 
+  void OnLoadModule(const ModuleSpec &module_spec, lldb::addr_t module_addr);
+  void OnUnloadModule(lldb::addr_t module_addr);
+
   void DidAttach() override;
   void DidLaunch() override;
   Status CanLoadImage() override;
@@ -35,6 +40,12 @@
 
   ConstString GetPluginName() override;
   uint32_t GetPluginVersion() override;
+
+protected:
+  lldb::addr_t GetLoadAddress(lldb::ModuleSP executable);
+
+private:
+  std::map<lldb::ModuleSP, lldb::addr_t> m_loaded_modules;
 };
 
 } // namespace lldb_private
Index: source/Plugins/DynamicLoader/Windows-DYLD/DynamicLoaderWindowsDYLD.cpp
===================================================================
--- source/Plugins/DynamicLoader/Windows-DYLD/DynamicLoaderWindowsDYLD.cpp
+++ source/Plugins/DynamicLoader/Windows-DYLD/DynamicLoaderWindowsDYLD.cpp
@@ -12,6 +12,7 @@
 #include "lldb/Core/Module.h"
 #include "lldb/Core/PluginManager.h"
 #include "lldb/Target/ExecutionContext.h"
+#include "lldb/Target/Platform.h"
 #include "lldb/Target/Process.h"
 #include "lldb/Target/RegisterContext.h"
 #include "lldb/Target/Target.h"
@@ -61,6 +62,56 @@
   return nullptr;
 }
 
+void DynamicLoaderWindowsDYLD::OnLoadModule(const ModuleSpec &module_spec,
+                                            lldb::addr_t module_addr) {
+  // Confusingly, there is no Target::AddSharedModule.  Instead, calling
+  // GetSharedModule() with a new module will add it to the module list and
+  // return a corresponding ModuleSP.
+  Status error;
+  ModuleSP module_sp =
+      m_process->GetTarget().GetSharedModule(module_spec, &error);
+  if (error.Fail())
+    return;
+
+  m_loaded_modules[module_sp] = module_addr;
+  UpdateLoadedSectionsCommon(module_sp, module_addr, false);
+}
+
+void DynamicLoaderWindowsDYLD::OnUnloadModule(lldb::addr_t module_addr) {
+  Address resolved_addr;
+  if (!m_process->GetTarget().ResolveLoadAddress(module_addr, resolved_addr))
+    return;
+
+  ModuleSP module_sp = resolved_addr.GetModule();
+  if (module_sp) {
+    m_loaded_modules.erase(module_sp);
+    UnloadSectionsCommon(module_sp);
+  }
+}
+
+lldb::addr_t DynamicLoaderWindowsDYLD::GetLoadAddress(ModuleSP executable) {
+  // First, see if the load address is already cached.
+  auto it = m_loaded_modules.find(executable);
+  if (it != m_loaded_modules.end() && it->second != LLDB_INVALID_ADDRESS)
+    return it->second;
+
+  lldb::addr_t load_addr = LLDB_INVALID_ADDRESS;
+
+  // Second, try to get it through the process plugins.  For a remote process,
+  // the remote platform will be responsible for providing it.
+  FileSpec file_spec(executable->GetPlatformFileSpec());
+  bool is_loaded = false;
+  Status status =
+      m_process->GetFileLoadAddress(file_spec, is_loaded, load_addr);
+  // Servers other than lldb server could respond with a bogus address.
+  if (status.Success() && is_loaded && load_addr != LLDB_INVALID_ADDRESS) {
+    m_loaded_modules[executable] = load_addr;
+    return load_addr;
+  }
+
+  return LLDB_INVALID_ADDRESS;
+}
+
 void DynamicLoaderWindowsDYLD::DidAttach() {
     Log *log(GetLogIfAnyCategoriesSet(LIBLLDB_LOG_DYNAMIC_LOADER));
   if (log)
@@ -73,21 +124,17 @@
 
   // Try to fetch the load address of the file from the process, since there
   // could be randomization of the load address.
+  lldb::addr_t load_addr = GetLoadAddress(executable);
+  if (load_addr == LLDB_INVALID_ADDRESS)
+    return;
 
-  // It might happen that the remote has a different dir for the file, so we
-  // only send the basename of the executable in the query. I think this is safe
-  // because I doubt that two executables with the same basenames are loaded in
-  // memory...
-  FileSpec file_spec(
-      executable->GetPlatformFileSpec().GetFilename().GetCString());
-  bool is_loaded;
-  addr_t base_addr = 0;
-  lldb::addr_t load_addr;
-  Status error = m_process->GetFileLoadAddress(file_spec, is_loaded, load_addr);
-  if (error.Success() && is_loaded) {
-    base_addr = load_addr;
-    UpdateLoadedSections(executable, LLDB_INVALID_ADDRESS, base_addr, false);
-  }
+  // Request the process base address.
+  lldb::addr_t image_base = m_process->GetImageInfoAddress();
+  if (image_base == load_addr)
+    return;
+
+  // Rebase the process's modules if there is a mismatch.
+  UpdateLoadedSections(executable, LLDB_INVALID_ADDRESS, load_addr, false);
 
   ModuleList module_list;
   module_list.Append(executable);
@@ -95,7 +142,26 @@
   m_process->LoadModules();
 }
 
-void DynamicLoaderWindowsDYLD::DidLaunch() {}
+void DynamicLoaderWindowsDYLD::DidLaunch() {
+  Log *log(GetLogIfAnyCategoriesSet(LIBLLDB_LOG_DYNAMIC_LOADER));
+  if (log)
+    log->Printf("DynamicLoaderWindowsDYLD::%s()", __FUNCTION__);
+
+  ModuleSP executable = GetTargetExecutable();
+  if (!executable.get())
+    return;
+
+  lldb::addr_t load_addr = GetLoadAddress(executable);
+  if (load_addr != LLDB_INVALID_ADDRESS) {
+    // Update the loaded sections so that the breakpoints can be resolved.
+    UpdateLoadedSections(executable, LLDB_INVALID_ADDRESS, load_addr, false);
+
+    ModuleList module_list;
+    module_list.Append(executable);
+    m_process->GetTarget().ModulesDidLoad(module_list);
+    m_process->LoadModules();
+  }
+}
 
 Status DynamicLoaderWindowsDYLD::CanLoadImage() { return Status(); }
 
_______________________________________________
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits

Reply via email to