LLDB  mainline
DynamicLoader.cpp
Go to the documentation of this file.
1 //===-- DynamicLoader.cpp -------------------------------------------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 
10 
11 #include "lldb/Core/Module.h"
12 #include "lldb/Core/ModuleList.h"
13 #include "lldb/Core/ModuleSpec.h"
15 #include "lldb/Core/Section.h"
16 #include "lldb/Symbol/ObjectFile.h"
18 #include "lldb/Target/Process.h"
19 #include "lldb/Target/Target.h"
22 
23 #include "llvm/ADT/StringRef.h"
24 
25 #include <memory>
26 
27 #include <cassert>
28 
29 using namespace lldb;
30 using namespace lldb_private;
31 
32 DynamicLoader *DynamicLoader::FindPlugin(Process *process,
33  llvm::StringRef plugin_name) {
34  DynamicLoaderCreateInstance create_callback = nullptr;
35  if (!plugin_name.empty()) {
36  create_callback =
37  PluginManager::GetDynamicLoaderCreateCallbackForPluginName(plugin_name);
38  if (create_callback) {
39  std::unique_ptr<DynamicLoader> instance_up(
40  create_callback(process, true));
41  if (instance_up)
42  return instance_up.release();
43  }
44  } else {
45  for (uint32_t idx = 0;
46  (create_callback =
47  PluginManager::GetDynamicLoaderCreateCallbackAtIndex(idx)) !=
48  nullptr;
49  ++idx) {
50  std::unique_ptr<DynamicLoader> instance_up(
51  create_callback(process, false));
52  if (instance_up)
53  return instance_up.release();
54  }
55  }
56  return nullptr;
57 }
58 
59 DynamicLoader::DynamicLoader(Process *process) : m_process(process) {}
60 
61 // Accessosors to the global setting as to whether to stop at image (shared
62 // library) loading/unloading.
63 
66 }
67 
70 }
71 
73  Target &target = m_process->GetTarget();
74  ModuleSP executable = target.GetExecutableModule();
75 
76  if (executable) {
77  if (FileSystem::Instance().Exists(executable->GetFileSpec())) {
78  ModuleSpec module_spec(executable->GetFileSpec(),
79  executable->GetArchitecture());
80  auto module_sp = std::make_shared<Module>(module_spec);
81 
82  // Check if the executable has changed and set it to the target
83  // executable if they differ.
84  if (module_sp && module_sp->GetUUID().IsValid() &&
85  executable->GetUUID().IsValid()) {
86  if (module_sp->GetUUID() != executable->GetUUID())
87  executable.reset();
88  } else if (executable->FileHasChanged()) {
89  executable.reset();
90  }
91 
92  if (!executable) {
93  executable = target.GetOrCreateModule(module_spec, true /* notify */);
94  if (executable.get() != target.GetExecutableModulePointer()) {
95  // Don't load dependent images since we are in dyld where we will
96  // know and find out about all images that are loaded
97  target.SetExecutableModule(executable, eLoadDependentsNo);
98  }
99  }
100  }
101  }
102  return executable;
103 }
104 
105 void DynamicLoader::UpdateLoadedSections(ModuleSP module, addr_t link_map_addr,
106  addr_t base_addr,
107  bool base_addr_is_offset) {
108  UpdateLoadedSectionsCommon(module, base_addr, base_addr_is_offset);
109 }
110 
112  addr_t base_addr,
113  bool base_addr_is_offset) {
114  bool changed;
115  module->SetLoadAddress(m_process->GetTarget(), base_addr, base_addr_is_offset,
116  changed);
117 }
118 
119 void DynamicLoader::UnloadSections(const ModuleSP module) {
120  UnloadSectionsCommon(module);
121 }
122 
123 void DynamicLoader::UnloadSectionsCommon(const ModuleSP module) {
124  Target &target = m_process->GetTarget();
125  const SectionList *sections = GetSectionListFromModule(module);
126 
127  assert(sections && "SectionList missing from unloaded module.");
128 
129  const size_t num_sections = sections->GetSize();
130  for (size_t i = 0; i < num_sections; ++i) {
131  SectionSP section_sp(sections->GetSectionAtIndex(i));
132  target.SetSectionUnloaded(section_sp);
133  }
134 }
135 
136 const SectionList *
137 DynamicLoader::GetSectionListFromModule(const ModuleSP module) const {
138  SectionList *sections = nullptr;
139  if (module) {
140  ObjectFile *obj_file = module->GetObjectFile();
141  if (obj_file != nullptr) {
142  sections = obj_file->GetSectionList();
143  }
144  }
145  return sections;
146 }
147 
149  Target &target = m_process->GetTarget();
150  ModuleSpec module_spec(file, target.GetArchitecture());
151 
152  if (ModuleSP module_sp = target.GetImages().FindFirstModule(module_spec))
153  return module_sp;
154 
155  if (ModuleSP module_sp = target.GetOrCreateModule(module_spec, false))
156  return module_sp;
157 
158  return nullptr;
159 }
160 
162  addr_t link_map_addr,
163  addr_t base_addr,
164  bool base_addr_is_offset) {
165  if (ModuleSP module_sp = FindModuleViaTarget(file)) {
166  UpdateLoadedSections(module_sp, link_map_addr, base_addr,
167  base_addr_is_offset);
168  return module_sp;
169  }
170 
171  return nullptr;
172 }
173 
175  int size_in_bytes) {
176  Status error;
177  uint64_t value =
178  m_process->ReadUnsignedIntegerFromMemory(addr, size_in_bytes, 0, error);
179  if (error.Fail())
180  return -1;
181  else
182  return (int64_t)value;
183 }
184 
186  Status error;
188  if (error.Fail())
189  return LLDB_INVALID_ADDRESS;
190  else
191  return value;
192 }
193 
195 {
196  if (m_process)
198 }
199 
lldb_private::DynamicLoader::SetStopWhenImagesChange
void SetStopWhenImagesChange(bool stop)
Set whether the process should stop when images change.
Definition: DynamicLoader.cpp:68
ModuleSpec.h
lldb_private::Target::GetOrCreateModule
lldb::ModuleSP GetOrCreateModule(const ModuleSpec &module_spec, bool notify, Status *error_ptr=nullptr)
Find a binary on the system and return its Module, or return an existing Module that is already in th...
Definition: Target.cpp:2065
lldb-private-interfaces.h
lldb_private::SectionList::GetSize
size_t GetSize() const
Definition: Section.h:74
lldb_private::Process
Definition: Process.h:338
lldb_private::Target::GetExecutableModulePointer
Module * GetExecutableModulePointer()
Definition: Target.cpp:1376
lldb_private::Target::GetExecutableModule
lldb::ModuleSP GetExecutableModule()
Gets the module for the main executable.
Definition: Target.cpp:1362
Module.h
lldb_private::Process::GetTarget
Target & GetTarget()
Get the target object pointer for this module.
Definition: Process.h:1206
lldb_private::ProcessProperties::SetStopOnSharedLibraryEvents
void SetStopOnSharedLibraryEvents(bool stop)
Definition: Process.cpp:262
lldb_private::DynamicLoader::UnloadSectionsCommon
void UnloadSectionsCommon(const lldb::ModuleSP module)
Definition: DynamicLoader.cpp:123
lldb_private::SectionList
Definition: Section.h:34
lldb::addr_t
uint64_t addr_t
Definition: lldb-types.h:83
lldb_private::Target
Definition: Target.h:473
Section.h
lldb_private::Target::GetImages
const ModuleList & GetImages() const
Get accessor for the images for this process.
Definition: Target.h:947
Process.h
lldb_private::DynamicLoader::LoadOperatingSystemPlugin
void LoadOperatingSystemPlugin(bool flush)
Definition: DynamicLoader.cpp:194
Target.h
lldb_private::FileSpec
Definition: FileSpec.h:56
error
static llvm::raw_ostream & error(Stream &strm)
Definition: CommandReturnObject.cpp:17
lldb_private::ObjectFile::GetSectionList
virtual SectionList * GetSectionList(bool update_module_section_list=true)
Gets the section list for the currently selected architecture (and object for archives).
Definition: ObjectFile.cpp:588
ModuleList.h
lldb_private::Process::LoadOperatingSystemPlugin
void LoadOperatingSystemPlugin(bool flush)
Definition: Process.cpp:2432
lldb_private::eLoadDependentsNo
@ eLoadDependentsNo
Definition: Target.h:65
MemoryRegionInfo.h
lldb_private::DynamicLoader::ReadUnsignedIntWithSizeInBytes
int64_t ReadUnsignedIntWithSizeInBytes(lldb::addr_t addr, int size_in_bytes)
Definition: DynamicLoader.cpp:174
lldb_private::DynamicLoader::FindModuleViaTarget
lldb::ModuleSP FindModuleViaTarget(const FileSpec &file)
Definition: DynamicLoader.cpp:148
lldb_private::DynamicLoader::ReadPointer
lldb::addr_t ReadPointer(lldb::addr_t addr)
Definition: DynamicLoader.cpp:185
lldb_private::ModuleList::FindFirstModule
lldb::ModuleSP FindFirstModule(const ModuleSpec &module_spec) const
Definition: ModuleList.cpp:618
lldb_private::DynamicLoader::UpdateLoadedSections
virtual void UpdateLoadedSections(lldb::ModuleSP module, lldb::addr_t link_map_addr, lldb::addr_t base_addr, bool base_addr_is_offset)
Updates the load address of every allocatable section in module.
Definition: DynamicLoader.cpp:105
lldb_private::SectionList::GetSectionAtIndex
lldb::SectionSP GetSectionAtIndex(size_t idx) const
Definition: Section.cpp:538
lldb_private::DynamicLoader
Definition: DynamicLoader.h:52
lldb_private::DynamicLoader::m_process
Process * m_process
The process that this dynamic loader plug-in is tracking.
Definition: DynamicLoader.h:317
lldb_private::DynamicLoader::UpdateLoadedSectionsCommon
void UpdateLoadedSectionsCommon(lldb::ModuleSP module, lldb::addr_t base_addr, bool base_addr_is_offset)
Definition: DynamicLoader.cpp:111
ObjectFile.h
lldb_private::Target::SetExecutableModule
void SetExecutableModule(lldb::ModuleSP &module_sp, LoadDependentFiles load_dependent_files=eLoadDependentsDefault)
Set the main executable module.
Definition: Target.cpp:1411
lldb_private::ModuleSpec
Definition: ModuleSpec.h:27
lldb_private::Target::GetArchitecture
const ArchSpec & GetArchitecture() const
Definition: Target.h:989
lldb_private::Target::SetSectionUnloaded
bool SetSectionUnloaded(const lldb::SectionSP &section_sp)
Definition: Target.cpp:2965
lldb_private::Status
Definition: Status.h:44
uint32_t
lldb_private::ProcessProperties::GetStopOnSharedLibraryEvents
bool GetStopOnSharedLibraryEvents() const
Definition: Process.cpp:256
lldb_private::DynamicLoader::LoadModuleAtAddress
virtual lldb::ModuleSP LoadModuleAtAddress(const lldb_private::FileSpec &file, lldb::addr_t link_map_addr, lldb::addr_t base_addr, bool base_addr_is_offset)
Locates or creates a module given by file and updates/loads the resulting module at the virtual base ...
Definition: DynamicLoader.cpp:161
lldb_private::DynamicLoader::GetStopWhenImagesChange
bool GetStopWhenImagesChange() const
Get whether the process should stop when images change.
Definition: DynamicLoader.cpp:64
PluginManager.h
lldb_private::DynamicLoader::GetTargetExecutable
lldb::ModuleSP GetTargetExecutable()
Checks to see if the target module has changed, updates the target accordingly and returns the target...
Definition: DynamicLoader.cpp:72
LLDB_INVALID_ADDRESS
#define LLDB_INVALID_ADDRESS
Definition: lldb-defines.h:74
lldb_private::FileSystem::Instance
static FileSystem & Instance()
Definition: common/FileSystem.cpp:46
lldb_private::DynamicLoader::UnloadSections
virtual void UnloadSections(const lldb::ModuleSP module)
Removes the loaded sections from the target in module.
Definition: DynamicLoader.cpp:119
lldb_private
A class that represents a running process on the host machine.
Definition: SBCommandInterpreterRunOptions.h:16
ConstString.h
lldb_private::Process::ReadUnsignedIntegerFromMemory
uint64_t ReadUnsignedIntegerFromMemory(lldb::addr_t load_addr, size_t byte_size, uint64_t fail_value, Status &error)
Reads an unsigned integer of the specified byte size from process memory.
Definition: Process.cpp:2062
lldb_private::Process::ReadPointerFromMemory
lldb::addr_t ReadPointerFromMemory(lldb::addr_t vm_addr, Status &error)
Definition: Process.cpp:2084
DynamicLoader.h
lldb_private::DynamicLoader::GetSectionListFromModule
const lldb_private::SectionList * GetSectionListFromModule(const lldb::ModuleSP module) const
Definition: DynamicLoader.cpp:137
lldb
Definition: SBAddress.h:15
lldb_private::ObjectFile
Definition: ObjectFile.h:60