[libc] Switch to using the generic `<gpuintrin.h>` implementations (#121810)
[llvm-project.git] / lldb / source / Target / Target.cpp
blob46216ba2d566d7be3721d668277edc7117c2d3fb
1 //===-- Target.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 //===----------------------------------------------------------------------===//
9 #include "lldb/Target/Target.h"
10 #include "lldb/Breakpoint/BreakpointIDList.h"
11 #include "lldb/Breakpoint/BreakpointPrecondition.h"
12 #include "lldb/Breakpoint/BreakpointResolver.h"
13 #include "lldb/Breakpoint/BreakpointResolverAddress.h"
14 #include "lldb/Breakpoint/BreakpointResolverFileLine.h"
15 #include "lldb/Breakpoint/BreakpointResolverFileRegex.h"
16 #include "lldb/Breakpoint/BreakpointResolverName.h"
17 #include "lldb/Breakpoint/BreakpointResolverScripted.h"
18 #include "lldb/Breakpoint/Watchpoint.h"
19 #include "lldb/Core/Debugger.h"
20 #include "lldb/Core/Module.h"
21 #include "lldb/Core/ModuleSpec.h"
22 #include "lldb/Core/PluginManager.h"
23 #include "lldb/Core/SearchFilter.h"
24 #include "lldb/Core/Section.h"
25 #include "lldb/Core/SourceManager.h"
26 #include "lldb/Core/StructuredDataImpl.h"
27 #include "lldb/DataFormatters/FormatterSection.h"
28 #include "lldb/Expression/DiagnosticManager.h"
29 #include "lldb/Expression/ExpressionVariable.h"
30 #include "lldb/Expression/REPL.h"
31 #include "lldb/Expression/UserExpression.h"
32 #include "lldb/Expression/UtilityFunction.h"
33 #include "lldb/Host/Host.h"
34 #include "lldb/Host/PosixApi.h"
35 #include "lldb/Host/StreamFile.h"
36 #include "lldb/Interpreter/CommandInterpreter.h"
37 #include "lldb/Interpreter/CommandReturnObject.h"
38 #include "lldb/Interpreter/Interfaces/ScriptedStopHookInterface.h"
39 #include "lldb/Interpreter/OptionGroupWatchpoint.h"
40 #include "lldb/Interpreter/OptionValues.h"
41 #include "lldb/Interpreter/Property.h"
42 #include "lldb/Symbol/Function.h"
43 #include "lldb/Symbol/ObjectFile.h"
44 #include "lldb/Symbol/Symbol.h"
45 #include "lldb/Target/ABI.h"
46 #include "lldb/Target/ExecutionContext.h"
47 #include "lldb/Target/Language.h"
48 #include "lldb/Target/LanguageRuntime.h"
49 #include "lldb/Target/Process.h"
50 #include "lldb/Target/RegisterTypeBuilder.h"
51 #include "lldb/Target/SectionLoadList.h"
52 #include "lldb/Target/StackFrame.h"
53 #include "lldb/Target/StackFrameRecognizer.h"
54 #include "lldb/Target/SystemRuntime.h"
55 #include "lldb/Target/Thread.h"
56 #include "lldb/Target/ThreadSpec.h"
57 #include "lldb/Target/UnixSignals.h"
58 #include "lldb/Utility/Event.h"
59 #include "lldb/Utility/FileSpec.h"
60 #include "lldb/Utility/LLDBAssert.h"
61 #include "lldb/Utility/LLDBLog.h"
62 #include "lldb/Utility/Log.h"
63 #include "lldb/Utility/RealpathPrefixes.h"
64 #include "lldb/Utility/State.h"
65 #include "lldb/Utility/StreamString.h"
66 #include "lldb/Utility/Timer.h"
68 #include "llvm/ADT/ScopeExit.h"
69 #include "llvm/ADT/SetVector.h"
70 #include "llvm/Support/ThreadPool.h"
72 #include <memory>
73 #include <mutex>
74 #include <optional>
75 #include <sstream>
77 using namespace lldb;
78 using namespace lldb_private;
80 namespace {
82 struct ExecutableInstaller {
84 ExecutableInstaller(PlatformSP platform, ModuleSP module)
85 : m_platform{platform}, m_module{module},
86 m_local_file{m_module->GetFileSpec()},
87 m_remote_file{m_module->GetRemoteInstallFileSpec()} {}
89 void setupRemoteFile() const { m_module->SetPlatformFileSpec(m_remote_file); }
91 PlatformSP m_platform;
92 ModuleSP m_module;
93 const FileSpec m_local_file;
94 const FileSpec m_remote_file;
97 struct MainExecutableInstaller {
99 MainExecutableInstaller(PlatformSP platform, ModuleSP module, TargetSP target,
100 ProcessLaunchInfo &launch_info)
101 : m_platform{platform}, m_module{module},
102 m_local_file{m_module->GetFileSpec()},
103 m_remote_file{
104 getRemoteFileSpec(m_platform, target, m_module, m_local_file)},
105 m_launch_info{launch_info} {}
107 void setupRemoteFile() const {
108 m_module->SetPlatformFileSpec(m_remote_file);
109 m_launch_info.SetExecutableFile(m_remote_file,
110 /*add_exe_file_as_first_arg=*/false);
111 m_platform->SetFilePermissions(m_remote_file, 0700 /*-rwx------*/);
114 PlatformSP m_platform;
115 ModuleSP m_module;
116 const FileSpec m_local_file;
117 const FileSpec m_remote_file;
119 private:
120 static FileSpec getRemoteFileSpec(PlatformSP platform, TargetSP target,
121 ModuleSP module,
122 const FileSpec &local_file) {
123 FileSpec remote_file = module->GetRemoteInstallFileSpec();
124 if (remote_file || !target->GetAutoInstallMainExecutable())
125 return remote_file;
127 if (!local_file)
128 return {};
130 remote_file = platform->GetRemoteWorkingDirectory();
131 remote_file.AppendPathComponent(local_file.GetFilename().GetCString());
133 return remote_file;
136 ProcessLaunchInfo &m_launch_info;
138 } // namespace
140 template <typename Installer>
141 static Status installExecutable(const Installer &installer) {
142 if (!installer.m_local_file || !installer.m_remote_file)
143 return Status();
145 Status error = installer.m_platform->Install(installer.m_local_file,
146 installer.m_remote_file);
147 if (error.Fail())
148 return error;
150 installer.setupRemoteFile();
151 return Status();
154 constexpr std::chrono::milliseconds EvaluateExpressionOptions::default_timeout;
156 Target::Arch::Arch(const ArchSpec &spec)
157 : m_spec(spec),
158 m_plugin_up(PluginManager::CreateArchitectureInstance(spec)) {}
160 const Target::Arch &Target::Arch::operator=(const ArchSpec &spec) {
161 m_spec = spec;
162 m_plugin_up = PluginManager::CreateArchitectureInstance(spec);
163 return *this;
166 llvm::StringRef Target::GetStaticBroadcasterClass() {
167 static constexpr llvm::StringLiteral class_name("lldb.target");
168 return class_name;
171 Target::Target(Debugger &debugger, const ArchSpec &target_arch,
172 const lldb::PlatformSP &platform_sp, bool is_dummy_target)
173 : TargetProperties(this),
174 Broadcaster(debugger.GetBroadcasterManager(),
175 Target::GetStaticBroadcasterClass().str()),
176 ExecutionContextScope(), m_debugger(debugger), m_platform_sp(platform_sp),
177 m_mutex(), m_arch(target_arch), m_images(this), m_section_load_history(),
178 m_breakpoint_list(false), m_internal_breakpoint_list(true),
179 m_watchpoint_list(), m_process_sp(), m_search_filter_sp(),
180 m_image_search_paths(ImageSearchPathsChanged, this),
181 m_source_manager_up(), m_stop_hooks(), m_stop_hook_next_id(0),
182 m_latest_stop_hook_id(0), m_valid(true), m_suppress_stop_hooks(false),
183 m_is_dummy_target(is_dummy_target),
184 m_frame_recognizer_manager_up(
185 std::make_unique<StackFrameRecognizerManager>()) {
186 SetEventName(eBroadcastBitBreakpointChanged, "breakpoint-changed");
187 SetEventName(eBroadcastBitModulesLoaded, "modules-loaded");
188 SetEventName(eBroadcastBitModulesUnloaded, "modules-unloaded");
189 SetEventName(eBroadcastBitWatchpointChanged, "watchpoint-changed");
190 SetEventName(eBroadcastBitSymbolsLoaded, "symbols-loaded");
192 CheckInWithManager();
194 LLDB_LOG(GetLog(LLDBLog::Object), "{0} Target::Target()",
195 static_cast<void *>(this));
196 if (target_arch.IsValid()) {
197 LLDB_LOG(GetLog(LLDBLog::Target),
198 "Target::Target created with architecture {0} ({1})",
199 target_arch.GetArchitectureName(),
200 target_arch.GetTriple().getTriple().c_str());
203 UpdateLaunchInfoFromProperties();
206 Target::~Target() {
207 Log *log = GetLog(LLDBLog::Object);
208 LLDB_LOG(log, "{0} Target::~Target()", static_cast<void *>(this));
209 DeleteCurrentProcess();
212 void Target::PrimeFromDummyTarget(Target &target) {
213 m_stop_hooks = target.m_stop_hooks;
215 for (const auto &breakpoint_sp : target.m_breakpoint_list.Breakpoints()) {
216 if (breakpoint_sp->IsInternal())
217 continue;
219 BreakpointSP new_bp(
220 Breakpoint::CopyFromBreakpoint(shared_from_this(), *breakpoint_sp));
221 AddBreakpoint(std::move(new_bp), false);
224 for (const auto &bp_name_entry : target.m_breakpoint_names) {
225 AddBreakpointName(std::make_unique<BreakpointName>(*bp_name_entry.second));
228 m_frame_recognizer_manager_up = std::make_unique<StackFrameRecognizerManager>(
229 *target.m_frame_recognizer_manager_up);
231 m_dummy_signals = target.m_dummy_signals;
234 void Target::Dump(Stream *s, lldb::DescriptionLevel description_level) {
235 // s->Printf("%.*p: ", (int)sizeof(void*) * 2, this);
236 if (description_level != lldb::eDescriptionLevelBrief) {
237 s->Indent();
238 s->PutCString("Target\n");
239 s->IndentMore();
240 m_images.Dump(s);
241 m_breakpoint_list.Dump(s);
242 m_internal_breakpoint_list.Dump(s);
243 s->IndentLess();
244 } else {
245 Module *exe_module = GetExecutableModulePointer();
246 if (exe_module)
247 s->PutCString(exe_module->GetFileSpec().GetFilename().GetCString());
248 else
249 s->PutCString("No executable module.");
253 void Target::CleanupProcess() {
254 // Do any cleanup of the target we need to do between process instances.
255 // NB It is better to do this before destroying the process in case the
256 // clean up needs some help from the process.
257 m_breakpoint_list.ClearAllBreakpointSites();
258 m_internal_breakpoint_list.ClearAllBreakpointSites();
259 ResetBreakpointHitCounts();
260 // Disable watchpoints just on the debugger side.
261 std::unique_lock<std::recursive_mutex> lock;
262 this->GetWatchpointList().GetListMutex(lock);
263 DisableAllWatchpoints(false);
264 ClearAllWatchpointHitCounts();
265 ClearAllWatchpointHistoricValues();
266 m_latest_stop_hook_id = 0;
269 void Target::DeleteCurrentProcess() {
270 if (m_process_sp) {
271 // We dispose any active tracing sessions on the current process
272 m_trace_sp.reset();
273 m_section_load_history.Clear();
274 if (m_process_sp->IsAlive())
275 m_process_sp->Destroy(false);
277 m_process_sp->Finalize(false /* not destructing */);
279 CleanupProcess();
281 m_process_sp.reset();
285 const lldb::ProcessSP &Target::CreateProcess(ListenerSP listener_sp,
286 llvm::StringRef plugin_name,
287 const FileSpec *crash_file,
288 bool can_connect) {
289 if (!listener_sp)
290 listener_sp = GetDebugger().GetListener();
291 DeleteCurrentProcess();
292 m_process_sp = Process::FindPlugin(shared_from_this(), plugin_name,
293 listener_sp, crash_file, can_connect);
294 return m_process_sp;
297 const lldb::ProcessSP &Target::GetProcessSP() const { return m_process_sp; }
299 lldb::REPLSP Target::GetREPL(Status &err, lldb::LanguageType language,
300 const char *repl_options, bool can_create) {
301 if (language == eLanguageTypeUnknown)
302 language = m_debugger.GetREPLLanguage();
304 if (language == eLanguageTypeUnknown) {
305 LanguageSet repl_languages = Language::GetLanguagesSupportingREPLs();
307 if (auto single_lang = repl_languages.GetSingularLanguage()) {
308 language = *single_lang;
309 } else if (repl_languages.Empty()) {
310 err = Status::FromErrorString(
311 "LLDB isn't configured with REPL support for any languages.");
312 return REPLSP();
313 } else {
314 err = Status::FromErrorString(
315 "Multiple possible REPL languages. Please specify a language.");
316 return REPLSP();
320 REPLMap::iterator pos = m_repl_map.find(language);
322 if (pos != m_repl_map.end()) {
323 return pos->second;
326 if (!can_create) {
327 err = Status::FromErrorStringWithFormat(
328 "Couldn't find an existing REPL for %s, and can't create a new one",
329 Language::GetNameForLanguageType(language));
330 return lldb::REPLSP();
333 Debugger *const debugger = nullptr;
334 lldb::REPLSP ret = REPL::Create(err, language, debugger, this, repl_options);
336 if (ret) {
337 m_repl_map[language] = ret;
338 return m_repl_map[language];
341 if (err.Success()) {
342 err = Status::FromErrorStringWithFormat(
343 "Couldn't create a REPL for %s",
344 Language::GetNameForLanguageType(language));
347 return lldb::REPLSP();
350 void Target::SetREPL(lldb::LanguageType language, lldb::REPLSP repl_sp) {
351 lldbassert(!m_repl_map.count(language));
353 m_repl_map[language] = repl_sp;
356 void Target::Destroy() {
357 std::lock_guard<std::recursive_mutex> guard(m_mutex);
358 m_valid = false;
359 DeleteCurrentProcess();
360 m_platform_sp.reset();
361 m_arch = ArchSpec();
362 ClearModules(true);
363 m_section_load_history.Clear();
364 const bool notify = false;
365 m_breakpoint_list.RemoveAll(notify);
366 m_internal_breakpoint_list.RemoveAll(notify);
367 m_last_created_breakpoint.reset();
368 m_watchpoint_list.RemoveAll(notify);
369 m_last_created_watchpoint.reset();
370 m_search_filter_sp.reset();
371 m_image_search_paths.Clear(notify);
372 m_stop_hooks.clear();
373 m_stop_hook_next_id = 0;
374 m_suppress_stop_hooks = false;
375 m_repl_map.clear();
376 Args signal_args;
377 ClearDummySignals(signal_args);
380 llvm::StringRef Target::GetABIName() const {
381 lldb::ABISP abi_sp;
382 if (m_process_sp)
383 abi_sp = m_process_sp->GetABI();
384 if (!abi_sp)
385 abi_sp = ABI::FindPlugin(ProcessSP(), GetArchitecture());
386 if (abi_sp)
387 return abi_sp->GetPluginName();
388 return {};
391 BreakpointList &Target::GetBreakpointList(bool internal) {
392 if (internal)
393 return m_internal_breakpoint_list;
394 else
395 return m_breakpoint_list;
398 const BreakpointList &Target::GetBreakpointList(bool internal) const {
399 if (internal)
400 return m_internal_breakpoint_list;
401 else
402 return m_breakpoint_list;
405 BreakpointSP Target::GetBreakpointByID(break_id_t break_id) {
406 BreakpointSP bp_sp;
408 if (LLDB_BREAK_ID_IS_INTERNAL(break_id))
409 bp_sp = m_internal_breakpoint_list.FindBreakpointByID(break_id);
410 else
411 bp_sp = m_breakpoint_list.FindBreakpointByID(break_id);
413 return bp_sp;
416 lldb::BreakpointSP
417 lldb_private::Target::CreateBreakpointAtUserEntry(Status &error) {
418 ModuleSP main_module_sp = GetExecutableModule();
419 FileSpecList shared_lib_filter;
420 shared_lib_filter.Append(main_module_sp->GetFileSpec());
421 llvm::SetVector<std::string, std::vector<std::string>,
422 std::unordered_set<std::string>>
423 entryPointNamesSet;
424 for (LanguageType lang_type : Language::GetSupportedLanguages()) {
425 Language *lang = Language::FindPlugin(lang_type);
426 if (!lang) {
427 error = Status::FromErrorString("Language not found\n");
428 return lldb::BreakpointSP();
430 std::string entryPointName = lang->GetUserEntryPointName().str();
431 if (!entryPointName.empty())
432 entryPointNamesSet.insert(entryPointName);
434 if (entryPointNamesSet.empty()) {
435 error = Status::FromErrorString("No entry point name found\n");
436 return lldb::BreakpointSP();
438 BreakpointSP bp_sp = CreateBreakpoint(
439 &shared_lib_filter,
440 /*containingSourceFiles=*/nullptr, entryPointNamesSet.takeVector(),
441 /*func_name_type_mask=*/eFunctionNameTypeFull,
442 /*language=*/eLanguageTypeUnknown,
443 /*offset=*/0,
444 /*skip_prologue=*/eLazyBoolNo,
445 /*internal=*/false,
446 /*hardware=*/false);
447 if (!bp_sp) {
448 error = Status::FromErrorString("Breakpoint creation failed.\n");
449 return lldb::BreakpointSP();
451 bp_sp->SetOneShot(true);
452 return bp_sp;
455 BreakpointSP Target::CreateSourceRegexBreakpoint(
456 const FileSpecList *containingModules,
457 const FileSpecList *source_file_spec_list,
458 const std::unordered_set<std::string> &function_names,
459 RegularExpression source_regex, bool internal, bool hardware,
460 LazyBool move_to_nearest_code) {
461 SearchFilterSP filter_sp(GetSearchFilterForModuleAndCUList(
462 containingModules, source_file_spec_list));
463 if (move_to_nearest_code == eLazyBoolCalculate)
464 move_to_nearest_code = GetMoveToNearestCode() ? eLazyBoolYes : eLazyBoolNo;
465 BreakpointResolverSP resolver_sp(new BreakpointResolverFileRegex(
466 nullptr, std::move(source_regex), function_names,
467 !static_cast<bool>(move_to_nearest_code)));
469 return CreateBreakpoint(filter_sp, resolver_sp, internal, hardware, true);
472 BreakpointSP Target::CreateBreakpoint(const FileSpecList *containingModules,
473 const FileSpec &file, uint32_t line_no,
474 uint32_t column, lldb::addr_t offset,
475 LazyBool check_inlines,
476 LazyBool skip_prologue, bool internal,
477 bool hardware,
478 LazyBool move_to_nearest_code) {
479 FileSpec remapped_file;
480 std::optional<llvm::StringRef> removed_prefix_opt =
481 GetSourcePathMap().ReverseRemapPath(file, remapped_file);
482 if (!removed_prefix_opt)
483 remapped_file = file;
485 if (check_inlines == eLazyBoolCalculate) {
486 const InlineStrategy inline_strategy = GetInlineStrategy();
487 switch (inline_strategy) {
488 case eInlineBreakpointsNever:
489 check_inlines = eLazyBoolNo;
490 break;
492 case eInlineBreakpointsHeaders:
493 if (remapped_file.IsSourceImplementationFile())
494 check_inlines = eLazyBoolNo;
495 else
496 check_inlines = eLazyBoolYes;
497 break;
499 case eInlineBreakpointsAlways:
500 check_inlines = eLazyBoolYes;
501 break;
504 SearchFilterSP filter_sp;
505 if (check_inlines == eLazyBoolNo) {
506 // Not checking for inlines, we are looking only for matching compile units
507 FileSpecList compile_unit_list;
508 compile_unit_list.Append(remapped_file);
509 filter_sp = GetSearchFilterForModuleAndCUList(containingModules,
510 &compile_unit_list);
511 } else {
512 filter_sp = GetSearchFilterForModuleList(containingModules);
514 if (skip_prologue == eLazyBoolCalculate)
515 skip_prologue = GetSkipPrologue() ? eLazyBoolYes : eLazyBoolNo;
516 if (move_to_nearest_code == eLazyBoolCalculate)
517 move_to_nearest_code = GetMoveToNearestCode() ? eLazyBoolYes : eLazyBoolNo;
519 SourceLocationSpec location_spec(remapped_file, line_no, column,
520 check_inlines,
521 !static_cast<bool>(move_to_nearest_code));
522 if (!location_spec)
523 return nullptr;
525 BreakpointResolverSP resolver_sp(new BreakpointResolverFileLine(
526 nullptr, offset, skip_prologue, location_spec, removed_prefix_opt));
527 return CreateBreakpoint(filter_sp, resolver_sp, internal, hardware, true);
530 BreakpointSP Target::CreateBreakpoint(lldb::addr_t addr, bool internal,
531 bool hardware) {
532 Address so_addr;
534 // Check for any reason we want to move this breakpoint to other address.
535 addr = GetBreakableLoadAddress(addr);
537 // Attempt to resolve our load address if possible, though it is ok if it
538 // doesn't resolve to section/offset.
540 // Try and resolve as a load address if possible
541 GetSectionLoadList().ResolveLoadAddress(addr, so_addr);
542 if (!so_addr.IsValid()) {
543 // The address didn't resolve, so just set this as an absolute address
544 so_addr.SetOffset(addr);
546 BreakpointSP bp_sp(CreateBreakpoint(so_addr, internal, hardware));
547 return bp_sp;
550 BreakpointSP Target::CreateBreakpoint(const Address &addr, bool internal,
551 bool hardware) {
552 SearchFilterSP filter_sp(
553 new SearchFilterForUnconstrainedSearches(shared_from_this()));
554 BreakpointResolverSP resolver_sp(
555 new BreakpointResolverAddress(nullptr, addr));
556 return CreateBreakpoint(filter_sp, resolver_sp, internal, hardware, false);
559 lldb::BreakpointSP
560 Target::CreateAddressInModuleBreakpoint(lldb::addr_t file_addr, bool internal,
561 const FileSpec &file_spec,
562 bool request_hardware) {
563 SearchFilterSP filter_sp(
564 new SearchFilterForUnconstrainedSearches(shared_from_this()));
565 BreakpointResolverSP resolver_sp(new BreakpointResolverAddress(
566 nullptr, file_addr, file_spec));
567 return CreateBreakpoint(filter_sp, resolver_sp, internal, request_hardware,
568 false);
571 BreakpointSP Target::CreateBreakpoint(
572 const FileSpecList *containingModules,
573 const FileSpecList *containingSourceFiles, const char *func_name,
574 FunctionNameType func_name_type_mask, LanguageType language,
575 lldb::addr_t offset, LazyBool skip_prologue, bool internal, bool hardware) {
576 BreakpointSP bp_sp;
577 if (func_name) {
578 SearchFilterSP filter_sp(GetSearchFilterForModuleAndCUList(
579 containingModules, containingSourceFiles));
581 if (skip_prologue == eLazyBoolCalculate)
582 skip_prologue = GetSkipPrologue() ? eLazyBoolYes : eLazyBoolNo;
583 if (language == lldb::eLanguageTypeUnknown)
584 language = GetLanguage().AsLanguageType();
586 BreakpointResolverSP resolver_sp(new BreakpointResolverName(
587 nullptr, func_name, func_name_type_mask, language, Breakpoint::Exact,
588 offset, skip_prologue));
589 bp_sp = CreateBreakpoint(filter_sp, resolver_sp, internal, hardware, true);
591 return bp_sp;
594 lldb::BreakpointSP
595 Target::CreateBreakpoint(const FileSpecList *containingModules,
596 const FileSpecList *containingSourceFiles,
597 const std::vector<std::string> &func_names,
598 FunctionNameType func_name_type_mask,
599 LanguageType language, lldb::addr_t offset,
600 LazyBool skip_prologue, bool internal, bool hardware) {
601 BreakpointSP bp_sp;
602 size_t num_names = func_names.size();
603 if (num_names > 0) {
604 SearchFilterSP filter_sp(GetSearchFilterForModuleAndCUList(
605 containingModules, containingSourceFiles));
607 if (skip_prologue == eLazyBoolCalculate)
608 skip_prologue = GetSkipPrologue() ? eLazyBoolYes : eLazyBoolNo;
609 if (language == lldb::eLanguageTypeUnknown)
610 language = GetLanguage().AsLanguageType();
612 BreakpointResolverSP resolver_sp(
613 new BreakpointResolverName(nullptr, func_names, func_name_type_mask,
614 language, offset, skip_prologue));
615 bp_sp = CreateBreakpoint(filter_sp, resolver_sp, internal, hardware, true);
617 return bp_sp;
620 BreakpointSP
621 Target::CreateBreakpoint(const FileSpecList *containingModules,
622 const FileSpecList *containingSourceFiles,
623 const char *func_names[], size_t num_names,
624 FunctionNameType func_name_type_mask,
625 LanguageType language, lldb::addr_t offset,
626 LazyBool skip_prologue, bool internal, bool hardware) {
627 BreakpointSP bp_sp;
628 if (num_names > 0) {
629 SearchFilterSP filter_sp(GetSearchFilterForModuleAndCUList(
630 containingModules, containingSourceFiles));
632 if (skip_prologue == eLazyBoolCalculate) {
633 if (offset == 0)
634 skip_prologue = GetSkipPrologue() ? eLazyBoolYes : eLazyBoolNo;
635 else
636 skip_prologue = eLazyBoolNo;
638 if (language == lldb::eLanguageTypeUnknown)
639 language = GetLanguage().AsLanguageType();
641 BreakpointResolverSP resolver_sp(new BreakpointResolverName(
642 nullptr, func_names, num_names, func_name_type_mask, language, offset,
643 skip_prologue));
644 resolver_sp->SetOffset(offset);
645 bp_sp = CreateBreakpoint(filter_sp, resolver_sp, internal, hardware, true);
647 return bp_sp;
650 SearchFilterSP
651 Target::GetSearchFilterForModule(const FileSpec *containingModule) {
652 SearchFilterSP filter_sp;
653 if (containingModule != nullptr) {
654 // TODO: We should look into sharing module based search filters
655 // across many breakpoints like we do for the simple target based one
656 filter_sp = std::make_shared<SearchFilterByModule>(shared_from_this(),
657 *containingModule);
658 } else {
659 if (!m_search_filter_sp)
660 m_search_filter_sp =
661 std::make_shared<SearchFilterForUnconstrainedSearches>(
662 shared_from_this());
663 filter_sp = m_search_filter_sp;
665 return filter_sp;
668 SearchFilterSP
669 Target::GetSearchFilterForModuleList(const FileSpecList *containingModules) {
670 SearchFilterSP filter_sp;
671 if (containingModules && containingModules->GetSize() != 0) {
672 // TODO: We should look into sharing module based search filters
673 // across many breakpoints like we do for the simple target based one
674 filter_sp = std::make_shared<SearchFilterByModuleList>(shared_from_this(),
675 *containingModules);
676 } else {
677 if (!m_search_filter_sp)
678 m_search_filter_sp =
679 std::make_shared<SearchFilterForUnconstrainedSearches>(
680 shared_from_this());
681 filter_sp = m_search_filter_sp;
683 return filter_sp;
686 SearchFilterSP Target::GetSearchFilterForModuleAndCUList(
687 const FileSpecList *containingModules,
688 const FileSpecList *containingSourceFiles) {
689 if (containingSourceFiles == nullptr || containingSourceFiles->GetSize() == 0)
690 return GetSearchFilterForModuleList(containingModules);
692 SearchFilterSP filter_sp;
693 if (containingModules == nullptr) {
694 // We could make a special "CU List only SearchFilter". Better yet was if
695 // these could be composable, but that will take a little reworking.
697 filter_sp = std::make_shared<SearchFilterByModuleListAndCU>(
698 shared_from_this(), FileSpecList(), *containingSourceFiles);
699 } else {
700 filter_sp = std::make_shared<SearchFilterByModuleListAndCU>(
701 shared_from_this(), *containingModules, *containingSourceFiles);
703 return filter_sp;
706 BreakpointSP Target::CreateFuncRegexBreakpoint(
707 const FileSpecList *containingModules,
708 const FileSpecList *containingSourceFiles, RegularExpression func_regex,
709 lldb::LanguageType requested_language, LazyBool skip_prologue,
710 bool internal, bool hardware) {
711 SearchFilterSP filter_sp(GetSearchFilterForModuleAndCUList(
712 containingModules, containingSourceFiles));
713 bool skip = (skip_prologue == eLazyBoolCalculate)
714 ? GetSkipPrologue()
715 : static_cast<bool>(skip_prologue);
716 BreakpointResolverSP resolver_sp(new BreakpointResolverName(
717 nullptr, std::move(func_regex), requested_language, 0, skip));
719 return CreateBreakpoint(filter_sp, resolver_sp, internal, hardware, true);
722 lldb::BreakpointSP
723 Target::CreateExceptionBreakpoint(enum lldb::LanguageType language,
724 bool catch_bp, bool throw_bp, bool internal,
725 Args *additional_args, Status *error) {
726 BreakpointSP exc_bkpt_sp = LanguageRuntime::CreateExceptionBreakpoint(
727 *this, language, catch_bp, throw_bp, internal);
728 if (exc_bkpt_sp && additional_args) {
729 BreakpointPreconditionSP precondition_sp = exc_bkpt_sp->GetPrecondition();
730 if (precondition_sp && additional_args) {
731 if (error)
732 *error = precondition_sp->ConfigurePrecondition(*additional_args);
733 else
734 precondition_sp->ConfigurePrecondition(*additional_args);
737 return exc_bkpt_sp;
740 lldb::BreakpointSP Target::CreateScriptedBreakpoint(
741 const llvm::StringRef class_name, const FileSpecList *containingModules,
742 const FileSpecList *containingSourceFiles, bool internal,
743 bool request_hardware, StructuredData::ObjectSP extra_args_sp,
744 Status *creation_error) {
745 SearchFilterSP filter_sp;
747 lldb::SearchDepth depth = lldb::eSearchDepthTarget;
748 bool has_files =
749 containingSourceFiles && containingSourceFiles->GetSize() > 0;
750 bool has_modules = containingModules && containingModules->GetSize() > 0;
752 if (has_files && has_modules) {
753 filter_sp = GetSearchFilterForModuleAndCUList(containingModules,
754 containingSourceFiles);
755 } else if (has_files) {
756 filter_sp =
757 GetSearchFilterForModuleAndCUList(nullptr, containingSourceFiles);
758 } else if (has_modules) {
759 filter_sp = GetSearchFilterForModuleList(containingModules);
760 } else {
761 filter_sp = std::make_shared<SearchFilterForUnconstrainedSearches>(
762 shared_from_this());
765 BreakpointResolverSP resolver_sp(new BreakpointResolverScripted(
766 nullptr, class_name, depth, StructuredDataImpl(extra_args_sp)));
767 return CreateBreakpoint(filter_sp, resolver_sp, internal, false, true);
770 BreakpointSP Target::CreateBreakpoint(SearchFilterSP &filter_sp,
771 BreakpointResolverSP &resolver_sp,
772 bool internal, bool request_hardware,
773 bool resolve_indirect_symbols) {
774 BreakpointSP bp_sp;
775 if (filter_sp && resolver_sp) {
776 const bool hardware = request_hardware || GetRequireHardwareBreakpoints();
777 bp_sp.reset(new Breakpoint(*this, filter_sp, resolver_sp, hardware,
778 resolve_indirect_symbols));
779 resolver_sp->SetBreakpoint(bp_sp);
780 AddBreakpoint(bp_sp, internal);
782 return bp_sp;
785 void Target::AddBreakpoint(lldb::BreakpointSP bp_sp, bool internal) {
786 if (!bp_sp)
787 return;
788 if (internal)
789 m_internal_breakpoint_list.Add(bp_sp, false);
790 else
791 m_breakpoint_list.Add(bp_sp, true);
793 Log *log = GetLog(LLDBLog::Breakpoints);
794 if (log) {
795 StreamString s;
796 bp_sp->GetDescription(&s, lldb::eDescriptionLevelVerbose);
797 LLDB_LOGF(log, "Target::%s (internal = %s) => break_id = %s\n",
798 __FUNCTION__, bp_sp->IsInternal() ? "yes" : "no", s.GetData());
801 bp_sp->ResolveBreakpoint();
803 if (!internal) {
804 m_last_created_breakpoint = bp_sp;
808 void Target::AddNameToBreakpoint(BreakpointID &id, llvm::StringRef name,
809 Status &error) {
810 BreakpointSP bp_sp =
811 m_breakpoint_list.FindBreakpointByID(id.GetBreakpointID());
812 if (!bp_sp) {
813 StreamString s;
814 id.GetDescription(&s, eDescriptionLevelBrief);
815 error = Status::FromErrorStringWithFormat("Could not find breakpoint %s",
816 s.GetData());
817 return;
819 AddNameToBreakpoint(bp_sp, name, error);
822 void Target::AddNameToBreakpoint(BreakpointSP &bp_sp, llvm::StringRef name,
823 Status &error) {
824 if (!bp_sp)
825 return;
827 BreakpointName *bp_name = FindBreakpointName(ConstString(name), true, error);
828 if (!bp_name)
829 return;
831 bp_name->ConfigureBreakpoint(bp_sp);
832 bp_sp->AddName(name);
835 void Target::AddBreakpointName(std::unique_ptr<BreakpointName> bp_name) {
836 m_breakpoint_names.insert(
837 std::make_pair(bp_name->GetName(), std::move(bp_name)));
840 BreakpointName *Target::FindBreakpointName(ConstString name, bool can_create,
841 Status &error) {
842 BreakpointID::StringIsBreakpointName(name.GetStringRef(), error);
843 if (!error.Success())
844 return nullptr;
846 BreakpointNameList::iterator iter = m_breakpoint_names.find(name);
847 if (iter != m_breakpoint_names.end()) {
848 return iter->second.get();
851 if (!can_create) {
852 error = Status::FromErrorStringWithFormat(
853 "Breakpoint name \"%s\" doesn't exist and "
854 "can_create is false.",
855 name.AsCString());
856 return nullptr;
859 return m_breakpoint_names
860 .insert(std::make_pair(name, std::make_unique<BreakpointName>(name)))
861 .first->second.get();
864 void Target::DeleteBreakpointName(ConstString name) {
865 BreakpointNameList::iterator iter = m_breakpoint_names.find(name);
867 if (iter != m_breakpoint_names.end()) {
868 const char *name_cstr = name.AsCString();
869 m_breakpoint_names.erase(iter);
870 for (auto bp_sp : m_breakpoint_list.Breakpoints())
871 bp_sp->RemoveName(name_cstr);
875 void Target::RemoveNameFromBreakpoint(lldb::BreakpointSP &bp_sp,
876 ConstString name) {
877 bp_sp->RemoveName(name.AsCString());
880 void Target::ConfigureBreakpointName(
881 BreakpointName &bp_name, const BreakpointOptions &new_options,
882 const BreakpointName::Permissions &new_permissions) {
883 bp_name.GetOptions().CopyOverSetOptions(new_options);
884 bp_name.GetPermissions().MergeInto(new_permissions);
885 ApplyNameToBreakpoints(bp_name);
888 void Target::ApplyNameToBreakpoints(BreakpointName &bp_name) {
889 llvm::Expected<std::vector<BreakpointSP>> expected_vector =
890 m_breakpoint_list.FindBreakpointsByName(bp_name.GetName().AsCString());
892 if (!expected_vector) {
893 LLDB_LOG(GetLog(LLDBLog::Breakpoints), "invalid breakpoint name: {}",
894 llvm::toString(expected_vector.takeError()));
895 return;
898 for (auto bp_sp : *expected_vector)
899 bp_name.ConfigureBreakpoint(bp_sp);
902 void Target::GetBreakpointNames(std::vector<std::string> &names) {
903 names.clear();
904 for (const auto& bp_name_entry : m_breakpoint_names) {
905 names.push_back(bp_name_entry.first.AsCString());
907 llvm::sort(names);
910 bool Target::ProcessIsValid() {
911 return (m_process_sp && m_process_sp->IsAlive());
914 static bool CheckIfWatchpointsSupported(Target *target, Status &error) {
915 std::optional<uint32_t> num_supported_hardware_watchpoints =
916 target->GetProcessSP()->GetWatchpointSlotCount();
918 // If unable to determine the # of watchpoints available,
919 // assume they are supported.
920 if (!num_supported_hardware_watchpoints)
921 return true;
923 if (*num_supported_hardware_watchpoints == 0) {
924 error = Status::FromErrorStringWithFormat(
925 "Target supports (%u) hardware watchpoint slots.\n",
926 *num_supported_hardware_watchpoints);
927 return false;
929 return true;
932 // See also Watchpoint::SetWatchpointType(uint32_t type) and the
933 // OptionGroupWatchpoint::WatchType enum type.
934 WatchpointSP Target::CreateWatchpoint(lldb::addr_t addr, size_t size,
935 const CompilerType *type, uint32_t kind,
936 Status &error) {
937 Log *log = GetLog(LLDBLog::Watchpoints);
938 LLDB_LOGF(log,
939 "Target::%s (addr = 0x%8.8" PRIx64 " size = %" PRIu64
940 " type = %u)\n",
941 __FUNCTION__, addr, (uint64_t)size, kind);
943 WatchpointSP wp_sp;
944 if (!ProcessIsValid()) {
945 error = Status::FromErrorString("process is not alive");
946 return wp_sp;
949 if (addr == LLDB_INVALID_ADDRESS || size == 0) {
950 if (size == 0)
951 error = Status::FromErrorString(
952 "cannot set a watchpoint with watch_size of 0");
953 else
954 error = Status::FromErrorStringWithFormat(
955 "invalid watch address: %" PRIu64, addr);
956 return wp_sp;
959 if (!LLDB_WATCH_TYPE_IS_VALID(kind)) {
960 error =
961 Status::FromErrorStringWithFormat("invalid watchpoint type: %d", kind);
964 if (!CheckIfWatchpointsSupported(this, error))
965 return wp_sp;
967 // Currently we only support one watchpoint per address, with total number of
968 // watchpoints limited by the hardware which the inferior is running on.
970 // Grab the list mutex while doing operations.
971 const bool notify = false; // Don't notify about all the state changes we do
972 // on creating the watchpoint.
974 // Mask off ignored bits from watchpoint address.
975 if (ABISP abi = m_process_sp->GetABI())
976 addr = abi->FixDataAddress(addr);
978 // LWP_TODO this sequence is looking for an existing watchpoint
979 // at the exact same user-specified address, disables the new one
980 // if addr/size/type match. If type/size differ, disable old one.
981 // This isn't correct, we need both watchpoints to use a shared
982 // WatchpointResource in the target, and expand the WatchpointResource
983 // to handle the needs of both Watchpoints.
984 // Also, even if the addresses don't match, they may need to be
985 // supported by the same WatchpointResource, e.g. a watchpoint
986 // watching 1 byte at 0x102 and a watchpoint watching 1 byte at 0x103.
987 // They're in the same word and must be watched by a single hardware
988 // watchpoint register.
990 std::unique_lock<std::recursive_mutex> lock;
991 this->GetWatchpointList().GetListMutex(lock);
992 WatchpointSP matched_sp = m_watchpoint_list.FindByAddress(addr);
993 if (matched_sp) {
994 size_t old_size = matched_sp->GetByteSize();
995 uint32_t old_type =
996 (matched_sp->WatchpointRead() ? LLDB_WATCH_TYPE_READ : 0) |
997 (matched_sp->WatchpointWrite() ? LLDB_WATCH_TYPE_WRITE : 0) |
998 (matched_sp->WatchpointModify() ? LLDB_WATCH_TYPE_MODIFY : 0);
999 // Return the existing watchpoint if both size and type match.
1000 if (size == old_size && kind == old_type) {
1001 wp_sp = matched_sp;
1002 wp_sp->SetEnabled(false, notify);
1003 } else {
1004 // Nil the matched watchpoint; we will be creating a new one.
1005 m_process_sp->DisableWatchpoint(matched_sp, notify);
1006 m_watchpoint_list.Remove(matched_sp->GetID(), true);
1010 if (!wp_sp) {
1011 wp_sp = std::make_shared<Watchpoint>(*this, addr, size, type);
1012 wp_sp->SetWatchpointType(kind, notify);
1013 m_watchpoint_list.Add(wp_sp, true);
1016 error = m_process_sp->EnableWatchpoint(wp_sp, notify);
1017 LLDB_LOGF(log, "Target::%s (creation of watchpoint %s with id = %u)\n",
1018 __FUNCTION__, error.Success() ? "succeeded" : "failed",
1019 wp_sp->GetID());
1021 if (error.Fail()) {
1022 // Enabling the watchpoint on the device side failed. Remove the said
1023 // watchpoint from the list maintained by the target instance.
1024 m_watchpoint_list.Remove(wp_sp->GetID(), true);
1025 wp_sp.reset();
1026 } else
1027 m_last_created_watchpoint = wp_sp;
1028 return wp_sp;
1031 void Target::RemoveAllowedBreakpoints() {
1032 Log *log = GetLog(LLDBLog::Breakpoints);
1033 LLDB_LOGF(log, "Target::%s \n", __FUNCTION__);
1035 m_breakpoint_list.RemoveAllowed(true);
1037 m_last_created_breakpoint.reset();
1040 void Target::RemoveAllBreakpoints(bool internal_also) {
1041 Log *log = GetLog(LLDBLog::Breakpoints);
1042 LLDB_LOGF(log, "Target::%s (internal_also = %s)\n", __FUNCTION__,
1043 internal_also ? "yes" : "no");
1045 m_breakpoint_list.RemoveAll(true);
1046 if (internal_also)
1047 m_internal_breakpoint_list.RemoveAll(false);
1049 m_last_created_breakpoint.reset();
1052 void Target::DisableAllBreakpoints(bool internal_also) {
1053 Log *log = GetLog(LLDBLog::Breakpoints);
1054 LLDB_LOGF(log, "Target::%s (internal_also = %s)\n", __FUNCTION__,
1055 internal_also ? "yes" : "no");
1057 m_breakpoint_list.SetEnabledAll(false);
1058 if (internal_also)
1059 m_internal_breakpoint_list.SetEnabledAll(false);
1062 void Target::DisableAllowedBreakpoints() {
1063 Log *log = GetLog(LLDBLog::Breakpoints);
1064 LLDB_LOGF(log, "Target::%s", __FUNCTION__);
1066 m_breakpoint_list.SetEnabledAllowed(false);
1069 void Target::EnableAllBreakpoints(bool internal_also) {
1070 Log *log = GetLog(LLDBLog::Breakpoints);
1071 LLDB_LOGF(log, "Target::%s (internal_also = %s)\n", __FUNCTION__,
1072 internal_also ? "yes" : "no");
1074 m_breakpoint_list.SetEnabledAll(true);
1075 if (internal_also)
1076 m_internal_breakpoint_list.SetEnabledAll(true);
1079 void Target::EnableAllowedBreakpoints() {
1080 Log *log = GetLog(LLDBLog::Breakpoints);
1081 LLDB_LOGF(log, "Target::%s", __FUNCTION__);
1083 m_breakpoint_list.SetEnabledAllowed(true);
1086 bool Target::RemoveBreakpointByID(break_id_t break_id) {
1087 Log *log = GetLog(LLDBLog::Breakpoints);
1088 LLDB_LOGF(log, "Target::%s (break_id = %i, internal = %s)\n", __FUNCTION__,
1089 break_id, LLDB_BREAK_ID_IS_INTERNAL(break_id) ? "yes" : "no");
1091 if (DisableBreakpointByID(break_id)) {
1092 if (LLDB_BREAK_ID_IS_INTERNAL(break_id))
1093 m_internal_breakpoint_list.Remove(break_id, false);
1094 else {
1095 if (m_last_created_breakpoint) {
1096 if (m_last_created_breakpoint->GetID() == break_id)
1097 m_last_created_breakpoint.reset();
1099 m_breakpoint_list.Remove(break_id, true);
1101 return true;
1103 return false;
1106 bool Target::DisableBreakpointByID(break_id_t break_id) {
1107 Log *log = GetLog(LLDBLog::Breakpoints);
1108 LLDB_LOGF(log, "Target::%s (break_id = %i, internal = %s)\n", __FUNCTION__,
1109 break_id, LLDB_BREAK_ID_IS_INTERNAL(break_id) ? "yes" : "no");
1111 BreakpointSP bp_sp;
1113 if (LLDB_BREAK_ID_IS_INTERNAL(break_id))
1114 bp_sp = m_internal_breakpoint_list.FindBreakpointByID(break_id);
1115 else
1116 bp_sp = m_breakpoint_list.FindBreakpointByID(break_id);
1117 if (bp_sp) {
1118 bp_sp->SetEnabled(false);
1119 return true;
1121 return false;
1124 bool Target::EnableBreakpointByID(break_id_t break_id) {
1125 Log *log = GetLog(LLDBLog::Breakpoints);
1126 LLDB_LOGF(log, "Target::%s (break_id = %i, internal = %s)\n", __FUNCTION__,
1127 break_id, LLDB_BREAK_ID_IS_INTERNAL(break_id) ? "yes" : "no");
1129 BreakpointSP bp_sp;
1131 if (LLDB_BREAK_ID_IS_INTERNAL(break_id))
1132 bp_sp = m_internal_breakpoint_list.FindBreakpointByID(break_id);
1133 else
1134 bp_sp = m_breakpoint_list.FindBreakpointByID(break_id);
1136 if (bp_sp) {
1137 bp_sp->SetEnabled(true);
1138 return true;
1140 return false;
1143 void Target::ResetBreakpointHitCounts() {
1144 GetBreakpointList().ResetHitCounts();
1147 Status Target::SerializeBreakpointsToFile(const FileSpec &file,
1148 const BreakpointIDList &bp_ids,
1149 bool append) {
1150 Status error;
1152 if (!file) {
1153 error = Status::FromErrorString("Invalid FileSpec.");
1154 return error;
1157 std::string path(file.GetPath());
1158 StructuredData::ObjectSP input_data_sp;
1160 StructuredData::ArraySP break_store_sp;
1161 StructuredData::Array *break_store_ptr = nullptr;
1163 if (append) {
1164 input_data_sp = StructuredData::ParseJSONFromFile(file, error);
1165 if (error.Success()) {
1166 break_store_ptr = input_data_sp->GetAsArray();
1167 if (!break_store_ptr) {
1168 error = Status::FromErrorStringWithFormat(
1169 "Tried to append to invalid input file %s", path.c_str());
1170 return error;
1175 if (!break_store_ptr) {
1176 break_store_sp = std::make_shared<StructuredData::Array>();
1177 break_store_ptr = break_store_sp.get();
1180 StreamFile out_file(path.c_str(),
1181 File::eOpenOptionTruncate | File::eOpenOptionWriteOnly |
1182 File::eOpenOptionCanCreate |
1183 File::eOpenOptionCloseOnExec,
1184 lldb::eFilePermissionsFileDefault);
1185 if (!out_file.GetFile().IsValid()) {
1186 error = Status::FromErrorStringWithFormat("Unable to open output file: %s.",
1187 path.c_str());
1188 return error;
1191 std::unique_lock<std::recursive_mutex> lock;
1192 GetBreakpointList().GetListMutex(lock);
1194 if (bp_ids.GetSize() == 0) {
1195 const BreakpointList &breakpoints = GetBreakpointList();
1197 size_t num_breakpoints = breakpoints.GetSize();
1198 for (size_t i = 0; i < num_breakpoints; i++) {
1199 Breakpoint *bp = breakpoints.GetBreakpointAtIndex(i).get();
1200 StructuredData::ObjectSP bkpt_save_sp = bp->SerializeToStructuredData();
1201 // If a breakpoint can't serialize it, just ignore it for now:
1202 if (bkpt_save_sp)
1203 break_store_ptr->AddItem(bkpt_save_sp);
1205 } else {
1207 std::unordered_set<lldb::break_id_t> processed_bkpts;
1208 const size_t count = bp_ids.GetSize();
1209 for (size_t i = 0; i < count; ++i) {
1210 BreakpointID cur_bp_id = bp_ids.GetBreakpointIDAtIndex(i);
1211 lldb::break_id_t bp_id = cur_bp_id.GetBreakpointID();
1213 if (bp_id != LLDB_INVALID_BREAK_ID) {
1214 // Only do each breakpoint once:
1215 std::pair<std::unordered_set<lldb::break_id_t>::iterator, bool>
1216 insert_result = processed_bkpts.insert(bp_id);
1217 if (!insert_result.second)
1218 continue;
1220 Breakpoint *bp = GetBreakpointByID(bp_id).get();
1221 StructuredData::ObjectSP bkpt_save_sp = bp->SerializeToStructuredData();
1222 // If the user explicitly asked to serialize a breakpoint, and we
1223 // can't, then raise an error:
1224 if (!bkpt_save_sp) {
1225 error = Status::FromErrorStringWithFormat(
1226 "Unable to serialize breakpoint %d", bp_id);
1227 return error;
1229 break_store_ptr->AddItem(bkpt_save_sp);
1234 break_store_ptr->Dump(out_file, false);
1235 out_file.PutChar('\n');
1236 return error;
1239 Status Target::CreateBreakpointsFromFile(const FileSpec &file,
1240 BreakpointIDList &new_bps) {
1241 std::vector<std::string> no_names;
1242 return CreateBreakpointsFromFile(file, no_names, new_bps);
1245 Status Target::CreateBreakpointsFromFile(const FileSpec &file,
1246 std::vector<std::string> &names,
1247 BreakpointIDList &new_bps) {
1248 std::unique_lock<std::recursive_mutex> lock;
1249 GetBreakpointList().GetListMutex(lock);
1251 Status error;
1252 StructuredData::ObjectSP input_data_sp =
1253 StructuredData::ParseJSONFromFile(file, error);
1254 if (!error.Success()) {
1255 return error;
1256 } else if (!input_data_sp || !input_data_sp->IsValid()) {
1257 error = Status::FromErrorStringWithFormat(
1258 "Invalid JSON from input file: %s.", file.GetPath().c_str());
1259 return error;
1262 StructuredData::Array *bkpt_array = input_data_sp->GetAsArray();
1263 if (!bkpt_array) {
1264 error = Status::FromErrorStringWithFormat(
1265 "Invalid breakpoint data from input file: %s.", file.GetPath().c_str());
1266 return error;
1269 size_t num_bkpts = bkpt_array->GetSize();
1270 size_t num_names = names.size();
1272 for (size_t i = 0; i < num_bkpts; i++) {
1273 StructuredData::ObjectSP bkpt_object_sp = bkpt_array->GetItemAtIndex(i);
1274 // Peel off the breakpoint key, and feed the rest to the Breakpoint:
1275 StructuredData::Dictionary *bkpt_dict = bkpt_object_sp->GetAsDictionary();
1276 if (!bkpt_dict) {
1277 error = Status::FromErrorStringWithFormat(
1278 "Invalid breakpoint data for element %zu from input file: %s.", i,
1279 file.GetPath().c_str());
1280 return error;
1282 StructuredData::ObjectSP bkpt_data_sp =
1283 bkpt_dict->GetValueForKey(Breakpoint::GetSerializationKey());
1284 if (num_names &&
1285 !Breakpoint::SerializedBreakpointMatchesNames(bkpt_data_sp, names))
1286 continue;
1288 BreakpointSP bkpt_sp = Breakpoint::CreateFromStructuredData(
1289 shared_from_this(), bkpt_data_sp, error);
1290 if (!error.Success()) {
1291 error = Status::FromErrorStringWithFormat(
1292 "Error restoring breakpoint %zu from %s: %s.", i,
1293 file.GetPath().c_str(), error.AsCString());
1294 return error;
1296 new_bps.AddBreakpointID(BreakpointID(bkpt_sp->GetID()));
1298 return error;
1301 // The flag 'end_to_end', default to true, signifies that the operation is
1302 // performed end to end, for both the debugger and the debuggee.
1304 // Assumption: Caller holds the list mutex lock for m_watchpoint_list for end
1305 // to end operations.
1306 bool Target::RemoveAllWatchpoints(bool end_to_end) {
1307 Log *log = GetLog(LLDBLog::Watchpoints);
1308 LLDB_LOGF(log, "Target::%s\n", __FUNCTION__);
1310 if (!end_to_end) {
1311 m_watchpoint_list.RemoveAll(true);
1312 return true;
1315 // Otherwise, it's an end to end operation.
1317 if (!ProcessIsValid())
1318 return false;
1320 for (WatchpointSP wp_sp : m_watchpoint_list.Watchpoints()) {
1321 if (!wp_sp)
1322 return false;
1324 Status rc = m_process_sp->DisableWatchpoint(wp_sp);
1325 if (rc.Fail())
1326 return false;
1328 m_watchpoint_list.RemoveAll(true);
1329 m_last_created_watchpoint.reset();
1330 return true; // Success!
1333 // Assumption: Caller holds the list mutex lock for m_watchpoint_list for end
1334 // to end operations.
1335 bool Target::DisableAllWatchpoints(bool end_to_end) {
1336 Log *log = GetLog(LLDBLog::Watchpoints);
1337 LLDB_LOGF(log, "Target::%s\n", __FUNCTION__);
1339 if (!end_to_end) {
1340 m_watchpoint_list.SetEnabledAll(false);
1341 return true;
1344 // Otherwise, it's an end to end operation.
1346 if (!ProcessIsValid())
1347 return false;
1349 for (WatchpointSP wp_sp : m_watchpoint_list.Watchpoints()) {
1350 if (!wp_sp)
1351 return false;
1353 Status rc = m_process_sp->DisableWatchpoint(wp_sp);
1354 if (rc.Fail())
1355 return false;
1357 return true; // Success!
1360 // Assumption: Caller holds the list mutex lock for m_watchpoint_list for end
1361 // to end operations.
1362 bool Target::EnableAllWatchpoints(bool end_to_end) {
1363 Log *log = GetLog(LLDBLog::Watchpoints);
1364 LLDB_LOGF(log, "Target::%s\n", __FUNCTION__);
1366 if (!end_to_end) {
1367 m_watchpoint_list.SetEnabledAll(true);
1368 return true;
1371 // Otherwise, it's an end to end operation.
1373 if (!ProcessIsValid())
1374 return false;
1376 for (WatchpointSP wp_sp : m_watchpoint_list.Watchpoints()) {
1377 if (!wp_sp)
1378 return false;
1380 Status rc = m_process_sp->EnableWatchpoint(wp_sp);
1381 if (rc.Fail())
1382 return false;
1384 return true; // Success!
1387 // Assumption: Caller holds the list mutex lock for m_watchpoint_list.
1388 bool Target::ClearAllWatchpointHitCounts() {
1389 Log *log = GetLog(LLDBLog::Watchpoints);
1390 LLDB_LOGF(log, "Target::%s\n", __FUNCTION__);
1392 for (WatchpointSP wp_sp : m_watchpoint_list.Watchpoints()) {
1393 if (!wp_sp)
1394 return false;
1396 wp_sp->ResetHitCount();
1398 return true; // Success!
1401 // Assumption: Caller holds the list mutex lock for m_watchpoint_list.
1402 bool Target::ClearAllWatchpointHistoricValues() {
1403 Log *log = GetLog(LLDBLog::Watchpoints);
1404 LLDB_LOGF(log, "Target::%s\n", __FUNCTION__);
1406 for (WatchpointSP wp_sp : m_watchpoint_list.Watchpoints()) {
1407 if (!wp_sp)
1408 return false;
1410 wp_sp->ResetHistoricValues();
1412 return true; // Success!
1415 // Assumption: Caller holds the list mutex lock for m_watchpoint_list during
1416 // these operations.
1417 bool Target::IgnoreAllWatchpoints(uint32_t ignore_count) {
1418 Log *log = GetLog(LLDBLog::Watchpoints);
1419 LLDB_LOGF(log, "Target::%s\n", __FUNCTION__);
1421 if (!ProcessIsValid())
1422 return false;
1424 for (WatchpointSP wp_sp : m_watchpoint_list.Watchpoints()) {
1425 if (!wp_sp)
1426 return false;
1428 wp_sp->SetIgnoreCount(ignore_count);
1430 return true; // Success!
1433 // Assumption: Caller holds the list mutex lock for m_watchpoint_list.
1434 bool Target::DisableWatchpointByID(lldb::watch_id_t watch_id) {
1435 Log *log = GetLog(LLDBLog::Watchpoints);
1436 LLDB_LOGF(log, "Target::%s (watch_id = %i)\n", __FUNCTION__, watch_id);
1438 if (!ProcessIsValid())
1439 return false;
1441 WatchpointSP wp_sp = m_watchpoint_list.FindByID(watch_id);
1442 if (wp_sp) {
1443 Status rc = m_process_sp->DisableWatchpoint(wp_sp);
1444 if (rc.Success())
1445 return true;
1447 // Else, fallthrough.
1449 return false;
1452 // Assumption: Caller holds the list mutex lock for m_watchpoint_list.
1453 bool Target::EnableWatchpointByID(lldb::watch_id_t watch_id) {
1454 Log *log = GetLog(LLDBLog::Watchpoints);
1455 LLDB_LOGF(log, "Target::%s (watch_id = %i)\n", __FUNCTION__, watch_id);
1457 if (!ProcessIsValid())
1458 return false;
1460 WatchpointSP wp_sp = m_watchpoint_list.FindByID(watch_id);
1461 if (wp_sp) {
1462 Status rc = m_process_sp->EnableWatchpoint(wp_sp);
1463 if (rc.Success())
1464 return true;
1466 // Else, fallthrough.
1468 return false;
1471 // Assumption: Caller holds the list mutex lock for m_watchpoint_list.
1472 bool Target::RemoveWatchpointByID(lldb::watch_id_t watch_id) {
1473 Log *log = GetLog(LLDBLog::Watchpoints);
1474 LLDB_LOGF(log, "Target::%s (watch_id = %i)\n", __FUNCTION__, watch_id);
1476 WatchpointSP watch_to_remove_sp = m_watchpoint_list.FindByID(watch_id);
1477 if (watch_to_remove_sp == m_last_created_watchpoint)
1478 m_last_created_watchpoint.reset();
1480 if (DisableWatchpointByID(watch_id)) {
1481 m_watchpoint_list.Remove(watch_id, true);
1482 return true;
1484 return false;
1487 // Assumption: Caller holds the list mutex lock for m_watchpoint_list.
1488 bool Target::IgnoreWatchpointByID(lldb::watch_id_t watch_id,
1489 uint32_t ignore_count) {
1490 Log *log = GetLog(LLDBLog::Watchpoints);
1491 LLDB_LOGF(log, "Target::%s (watch_id = %i)\n", __FUNCTION__, watch_id);
1493 if (!ProcessIsValid())
1494 return false;
1496 WatchpointSP wp_sp = m_watchpoint_list.FindByID(watch_id);
1497 if (wp_sp) {
1498 wp_sp->SetIgnoreCount(ignore_count);
1499 return true;
1501 return false;
1504 ModuleSP Target::GetExecutableModule() {
1505 // search for the first executable in the module list
1506 for (size_t i = 0; i < m_images.GetSize(); ++i) {
1507 ModuleSP module_sp = m_images.GetModuleAtIndex(i);
1508 lldb_private::ObjectFile *obj = module_sp->GetObjectFile();
1509 if (obj == nullptr)
1510 continue;
1511 if (obj->GetType() == ObjectFile::Type::eTypeExecutable)
1512 return module_sp;
1514 // as fall back return the first module loaded
1515 return m_images.GetModuleAtIndex(0);
1518 Module *Target::GetExecutableModulePointer() {
1519 return GetExecutableModule().get();
1522 static void LoadScriptingResourceForModule(const ModuleSP &module_sp,
1523 Target *target) {
1524 Status error;
1525 StreamString feedback_stream;
1526 if (module_sp && !module_sp->LoadScriptingResourceInTarget(target, error,
1527 feedback_stream)) {
1528 if (error.AsCString())
1529 target->GetDebugger().GetErrorStream().Printf(
1530 "unable to load scripting data for module %s - error reported was "
1531 "%s\n",
1532 module_sp->GetFileSpec().GetFileNameStrippingExtension().GetCString(),
1533 error.AsCString());
1535 if (feedback_stream.GetSize())
1536 target->GetDebugger().GetErrorStream().Printf("%s\n",
1537 feedback_stream.GetData());
1540 void Target::ClearModules(bool delete_locations) {
1541 ModulesDidUnload(m_images, delete_locations);
1542 m_section_load_history.Clear();
1543 m_images.Clear();
1544 m_scratch_type_system_map.Clear();
1547 void Target::DidExec() {
1548 // When a process exec's we need to know about it so we can do some cleanup.
1549 m_breakpoint_list.RemoveInvalidLocations(m_arch.GetSpec());
1550 m_internal_breakpoint_list.RemoveInvalidLocations(m_arch.GetSpec());
1553 void Target::SetExecutableModule(ModuleSP &executable_sp,
1554 LoadDependentFiles load_dependent_files) {
1555 Log *log = GetLog(LLDBLog::Target);
1556 ClearModules(false);
1558 if (executable_sp) {
1559 ElapsedTime elapsed(m_stats.GetCreateTime());
1560 LLDB_SCOPED_TIMERF("Target::SetExecutableModule (executable = '%s')",
1561 executable_sp->GetFileSpec().GetPath().c_str());
1563 const bool notify = true;
1564 m_images.Append(executable_sp,
1565 notify); // The first image is our executable file
1567 // If we haven't set an architecture yet, reset our architecture based on
1568 // what we found in the executable module.
1569 if (!m_arch.GetSpec().IsValid()) {
1570 m_arch = executable_sp->GetArchitecture();
1571 LLDB_LOG(log,
1572 "Target::SetExecutableModule setting architecture to {0} ({1}) "
1573 "based on executable file",
1574 m_arch.GetSpec().GetArchitectureName(),
1575 m_arch.GetSpec().GetTriple().getTriple());
1578 ObjectFile *executable_objfile = executable_sp->GetObjectFile();
1579 bool load_dependents = true;
1580 switch (load_dependent_files) {
1581 case eLoadDependentsDefault:
1582 load_dependents = executable_sp->IsExecutable();
1583 break;
1584 case eLoadDependentsYes:
1585 load_dependents = true;
1586 break;
1587 case eLoadDependentsNo:
1588 load_dependents = false;
1589 break;
1592 if (executable_objfile && load_dependents) {
1593 // FileSpecList is not thread safe and needs to be synchronized.
1594 FileSpecList dependent_files;
1595 std::mutex dependent_files_mutex;
1597 // ModuleList is thread safe.
1598 ModuleList added_modules;
1600 auto GetDependentModules = [&](FileSpec dependent_file_spec) {
1601 FileSpec platform_dependent_file_spec;
1602 if (m_platform_sp)
1603 m_platform_sp->GetFileWithUUID(dependent_file_spec, nullptr,
1604 platform_dependent_file_spec);
1605 else
1606 platform_dependent_file_spec = dependent_file_spec;
1608 ModuleSpec module_spec(platform_dependent_file_spec, m_arch.GetSpec());
1609 ModuleSP image_module_sp(
1610 GetOrCreateModule(module_spec, false /* notify */));
1611 if (image_module_sp) {
1612 added_modules.AppendIfNeeded(image_module_sp, false);
1613 ObjectFile *objfile = image_module_sp->GetObjectFile();
1614 if (objfile) {
1615 // Create a local copy of the dependent file list so we don't have
1616 // to lock for the whole duration of GetDependentModules.
1617 FileSpecList dependent_files_copy;
1619 std::lock_guard<std::mutex> guard(dependent_files_mutex);
1620 dependent_files_copy = dependent_files;
1623 // Remember the size of the local copy so we can append only the
1624 // modules that have been added by GetDependentModules.
1625 const size_t previous_dependent_files =
1626 dependent_files_copy.GetSize();
1628 objfile->GetDependentModules(dependent_files_copy);
1631 std::lock_guard<std::mutex> guard(dependent_files_mutex);
1632 for (size_t i = previous_dependent_files;
1633 i < dependent_files_copy.GetSize(); ++i)
1634 dependent_files.AppendIfUnique(
1635 dependent_files_copy.GetFileSpecAtIndex(i));
1641 executable_objfile->GetDependentModules(dependent_files);
1643 llvm::ThreadPoolTaskGroup task_group(Debugger::GetThreadPool());
1644 for (uint32_t i = 0; i < dependent_files.GetSize(); i++) {
1645 // Process all currently known dependencies in parallel in the innermost
1646 // loop. This may create newly discovered dependencies to be appended to
1647 // dependent_files. We'll deal with these files during the next
1648 // iteration of the outermost loop.
1650 std::lock_guard<std::mutex> guard(dependent_files_mutex);
1651 for (; i < dependent_files.GetSize(); i++)
1652 task_group.async(GetDependentModules,
1653 dependent_files.GetFileSpecAtIndex(i));
1655 task_group.wait();
1657 ModulesDidLoad(added_modules);
1662 bool Target::SetArchitecture(const ArchSpec &arch_spec, bool set_platform,
1663 bool merge) {
1664 Log *log = GetLog(LLDBLog::Target);
1665 bool missing_local_arch = !m_arch.GetSpec().IsValid();
1666 bool replace_local_arch = true;
1667 bool compatible_local_arch = false;
1668 ArchSpec other(arch_spec);
1670 // Changing the architecture might mean that the currently selected platform
1671 // isn't compatible. Set the platform correctly if we are asked to do so,
1672 // otherwise assume the user will set the platform manually.
1673 if (set_platform) {
1674 if (other.IsValid()) {
1675 auto platform_sp = GetPlatform();
1676 if (!platform_sp || !platform_sp->IsCompatibleArchitecture(
1677 other, {}, ArchSpec::CompatibleMatch, nullptr)) {
1678 ArchSpec platform_arch;
1679 if (PlatformSP arch_platform_sp =
1680 GetDebugger().GetPlatformList().GetOrCreate(other, {},
1681 &platform_arch)) {
1682 SetPlatform(arch_platform_sp);
1683 if (platform_arch.IsValid())
1684 other = platform_arch;
1690 if (!missing_local_arch) {
1691 if (merge && m_arch.GetSpec().IsCompatibleMatch(arch_spec)) {
1692 other.MergeFrom(m_arch.GetSpec());
1694 if (m_arch.GetSpec().IsCompatibleMatch(other)) {
1695 compatible_local_arch = true;
1697 if (m_arch.GetSpec().GetTriple() == other.GetTriple())
1698 replace_local_arch = false;
1703 if (compatible_local_arch || missing_local_arch) {
1704 // If we haven't got a valid arch spec, or the architectures are compatible
1705 // update the architecture, unless the one we already have is more
1706 // specified
1707 if (replace_local_arch)
1708 m_arch = other;
1709 LLDB_LOG(log,
1710 "Target::SetArchitecture merging compatible arch; arch "
1711 "is now {0} ({1})",
1712 m_arch.GetSpec().GetArchitectureName(),
1713 m_arch.GetSpec().GetTriple().getTriple());
1714 return true;
1717 // If we have an executable file, try to reset the executable to the desired
1718 // architecture
1719 LLDB_LOGF(
1720 log,
1721 "Target::SetArchitecture changing architecture to %s (%s) from %s (%s)",
1722 arch_spec.GetArchitectureName(),
1723 arch_spec.GetTriple().getTriple().c_str(),
1724 m_arch.GetSpec().GetArchitectureName(),
1725 m_arch.GetSpec().GetTriple().getTriple().c_str());
1726 m_arch = other;
1727 ModuleSP executable_sp = GetExecutableModule();
1729 ClearModules(true);
1730 // Need to do something about unsetting breakpoints.
1732 if (executable_sp) {
1733 LLDB_LOGF(log,
1734 "Target::SetArchitecture Trying to select executable file "
1735 "architecture %s (%s)",
1736 arch_spec.GetArchitectureName(),
1737 arch_spec.GetTriple().getTriple().c_str());
1738 ModuleSpec module_spec(executable_sp->GetFileSpec(), other);
1739 FileSpecList search_paths = GetExecutableSearchPaths();
1740 Status error = ModuleList::GetSharedModule(module_spec, executable_sp,
1741 &search_paths, nullptr, nullptr);
1743 if (!error.Fail() && executable_sp) {
1744 SetExecutableModule(executable_sp, eLoadDependentsYes);
1745 return true;
1748 return false;
1751 bool Target::MergeArchitecture(const ArchSpec &arch_spec) {
1752 Log *log = GetLog(LLDBLog::Target);
1753 if (arch_spec.IsValid()) {
1754 if (m_arch.GetSpec().IsCompatibleMatch(arch_spec)) {
1755 // The current target arch is compatible with "arch_spec", see if we can
1756 // improve our current architecture using bits from "arch_spec"
1758 LLDB_LOGF(log,
1759 "Target::MergeArchitecture target has arch %s, merging with "
1760 "arch %s",
1761 m_arch.GetSpec().GetTriple().getTriple().c_str(),
1762 arch_spec.GetTriple().getTriple().c_str());
1764 // Merge bits from arch_spec into "merged_arch" and set our architecture
1765 ArchSpec merged_arch(m_arch.GetSpec());
1766 merged_arch.MergeFrom(arch_spec);
1767 return SetArchitecture(merged_arch);
1768 } else {
1769 // The new architecture is different, we just need to replace it
1770 return SetArchitecture(arch_spec);
1773 return false;
1776 void Target::NotifyWillClearList(const ModuleList &module_list) {}
1778 void Target::NotifyModuleAdded(const ModuleList &module_list,
1779 const ModuleSP &module_sp) {
1780 // A module is being added to this target for the first time
1781 if (m_valid) {
1782 ModuleList my_module_list;
1783 my_module_list.Append(module_sp);
1784 ModulesDidLoad(my_module_list);
1788 void Target::NotifyModuleRemoved(const ModuleList &module_list,
1789 const ModuleSP &module_sp) {
1790 // A module is being removed from this target.
1791 if (m_valid) {
1792 ModuleList my_module_list;
1793 my_module_list.Append(module_sp);
1794 ModulesDidUnload(my_module_list, false);
1798 void Target::NotifyModuleUpdated(const ModuleList &module_list,
1799 const ModuleSP &old_module_sp,
1800 const ModuleSP &new_module_sp) {
1801 // A module is replacing an already added module
1802 if (m_valid) {
1803 m_breakpoint_list.UpdateBreakpointsWhenModuleIsReplaced(old_module_sp,
1804 new_module_sp);
1805 m_internal_breakpoint_list.UpdateBreakpointsWhenModuleIsReplaced(
1806 old_module_sp, new_module_sp);
1810 void Target::NotifyModulesRemoved(lldb_private::ModuleList &module_list) {
1811 ModulesDidUnload(module_list, false);
1814 void Target::ModulesDidLoad(ModuleList &module_list) {
1815 const size_t num_images = module_list.GetSize();
1816 if (m_valid && num_images) {
1817 for (size_t idx = 0; idx < num_images; ++idx) {
1818 ModuleSP module_sp(module_list.GetModuleAtIndex(idx));
1819 LoadScriptingResourceForModule(module_sp, this);
1820 LoadTypeSummariesForModule(module_sp);
1821 LoadFormattersForModule(module_sp);
1823 m_breakpoint_list.UpdateBreakpoints(module_list, true, false);
1824 m_internal_breakpoint_list.UpdateBreakpoints(module_list, true, false);
1825 if (m_process_sp) {
1826 m_process_sp->ModulesDidLoad(module_list);
1828 auto data_sp =
1829 std::make_shared<TargetEventData>(shared_from_this(), module_list);
1830 BroadcastEvent(eBroadcastBitModulesLoaded, data_sp);
1834 void Target::SymbolsDidLoad(ModuleList &module_list) {
1835 if (m_valid && module_list.GetSize()) {
1836 if (m_process_sp) {
1837 for (LanguageRuntime *runtime : m_process_sp->GetLanguageRuntimes()) {
1838 runtime->SymbolsDidLoad(module_list);
1842 m_breakpoint_list.UpdateBreakpoints(module_list, true, false);
1843 m_internal_breakpoint_list.UpdateBreakpoints(module_list, true, false);
1844 auto data_sp =
1845 std::make_shared<TargetEventData>(shared_from_this(), module_list);
1846 BroadcastEvent(eBroadcastBitSymbolsLoaded, data_sp);
1850 void Target::ModulesDidUnload(ModuleList &module_list, bool delete_locations) {
1851 if (m_valid && module_list.GetSize()) {
1852 UnloadModuleSections(module_list);
1853 auto data_sp =
1854 std::make_shared<TargetEventData>(shared_from_this(), module_list);
1855 BroadcastEvent(eBroadcastBitModulesUnloaded, data_sp);
1856 m_breakpoint_list.UpdateBreakpoints(module_list, false, delete_locations);
1857 m_internal_breakpoint_list.UpdateBreakpoints(module_list, false,
1858 delete_locations);
1860 // If a module was torn down it will have torn down the 'TypeSystemClang's
1861 // that we used as source 'ASTContext's for the persistent variables in
1862 // the current target. Those would now be unsafe to access because the
1863 // 'DeclOrigin' are now possibly stale. Thus clear all persistent
1864 // variables. We only want to flush 'TypeSystem's if the module being
1865 // unloaded was capable of describing a source type. JITted module unloads
1866 // happen frequently for Objective-C utility functions or the REPL and rely
1867 // on the persistent variables to stick around.
1868 const bool should_flush_type_systems =
1869 module_list.AnyOf([](lldb_private::Module &module) {
1870 auto *object_file = module.GetObjectFile();
1872 if (!object_file)
1873 return false;
1875 auto type = object_file->GetType();
1877 // eTypeExecutable: when debugged binary was rebuilt
1878 // eTypeSharedLibrary: if dylib was re-loaded
1879 return module.FileHasChanged() &&
1880 (type == ObjectFile::eTypeObjectFile ||
1881 type == ObjectFile::eTypeExecutable ||
1882 type == ObjectFile::eTypeSharedLibrary);
1885 if (should_flush_type_systems)
1886 m_scratch_type_system_map.Clear();
1890 bool Target::ModuleIsExcludedForUnconstrainedSearches(
1891 const FileSpec &module_file_spec) {
1892 if (GetBreakpointsConsultPlatformAvoidList()) {
1893 ModuleList matchingModules;
1894 ModuleSpec module_spec(module_file_spec);
1895 GetImages().FindModules(module_spec, matchingModules);
1896 size_t num_modules = matchingModules.GetSize();
1898 // If there is more than one module for this file spec, only
1899 // return true if ALL the modules are on the black list.
1900 if (num_modules > 0) {
1901 for (size_t i = 0; i < num_modules; i++) {
1902 if (!ModuleIsExcludedForUnconstrainedSearches(
1903 matchingModules.GetModuleAtIndex(i)))
1904 return false;
1906 return true;
1909 return false;
1912 bool Target::ModuleIsExcludedForUnconstrainedSearches(
1913 const lldb::ModuleSP &module_sp) {
1914 if (GetBreakpointsConsultPlatformAvoidList()) {
1915 if (m_platform_sp)
1916 return m_platform_sp->ModuleIsExcludedForUnconstrainedSearches(*this,
1917 module_sp);
1919 return false;
1922 size_t Target::ReadMemoryFromFileCache(const Address &addr, void *dst,
1923 size_t dst_len, Status &error) {
1924 SectionSP section_sp(addr.GetSection());
1925 if (section_sp) {
1926 // If the contents of this section are encrypted, the on-disk file is
1927 // unusable. Read only from live memory.
1928 if (section_sp->IsEncrypted()) {
1929 error = Status::FromErrorString("section is encrypted");
1930 return 0;
1932 ModuleSP module_sp(section_sp->GetModule());
1933 if (module_sp) {
1934 ObjectFile *objfile = section_sp->GetModule()->GetObjectFile();
1935 if (objfile) {
1936 size_t bytes_read = objfile->ReadSectionData(
1937 section_sp.get(), addr.GetOffset(), dst, dst_len);
1938 if (bytes_read > 0)
1939 return bytes_read;
1940 else
1941 error = Status::FromErrorStringWithFormat(
1942 "error reading data from section %s",
1943 section_sp->GetName().GetCString());
1944 } else
1945 error = Status::FromErrorString("address isn't from a object file");
1946 } else
1947 error = Status::FromErrorString("address isn't in a module");
1948 } else
1949 error = Status::FromErrorString(
1950 "address doesn't contain a section that points to a "
1951 "section in a object file");
1953 return 0;
1956 size_t Target::ReadMemory(const Address &addr, void *dst, size_t dst_len,
1957 Status &error, bool force_live_memory,
1958 lldb::addr_t *load_addr_ptr) {
1959 error.Clear();
1961 Address fixed_addr = addr;
1962 if (ProcessIsValid())
1963 if (const ABISP &abi = m_process_sp->GetABI())
1964 fixed_addr.SetLoadAddress(abi->FixAnyAddress(addr.GetLoadAddress(this)),
1965 this);
1967 // if we end up reading this from process memory, we will fill this with the
1968 // actual load address
1969 if (load_addr_ptr)
1970 *load_addr_ptr = LLDB_INVALID_ADDRESS;
1972 size_t bytes_read = 0;
1974 addr_t load_addr = LLDB_INVALID_ADDRESS;
1975 addr_t file_addr = LLDB_INVALID_ADDRESS;
1976 Address resolved_addr;
1977 if (!fixed_addr.IsSectionOffset()) {
1978 SectionLoadList &section_load_list = GetSectionLoadList();
1979 if (section_load_list.IsEmpty()) {
1980 // No sections are loaded, so we must assume we are not running yet and
1981 // anything we are given is a file address.
1982 file_addr =
1983 fixed_addr.GetOffset(); // "fixed_addr" doesn't have a section, so
1984 // its offset is the file address
1985 m_images.ResolveFileAddress(file_addr, resolved_addr);
1986 } else {
1987 // We have at least one section loaded. This can be because we have
1988 // manually loaded some sections with "target modules load ..." or
1989 // because we have a live process that has sections loaded through
1990 // the dynamic loader
1991 load_addr =
1992 fixed_addr.GetOffset(); // "fixed_addr" doesn't have a section, so
1993 // its offset is the load address
1994 section_load_list.ResolveLoadAddress(load_addr, resolved_addr);
1997 if (!resolved_addr.IsValid())
1998 resolved_addr = fixed_addr;
2000 // If we read from the file cache but can't get as many bytes as requested,
2001 // we keep the result around in this buffer, in case this result is the
2002 // best we can do.
2003 std::unique_ptr<uint8_t[]> file_cache_read_buffer;
2004 size_t file_cache_bytes_read = 0;
2006 // Read from file cache if read-only section.
2007 if (!force_live_memory && resolved_addr.IsSectionOffset()) {
2008 SectionSP section_sp(resolved_addr.GetSection());
2009 if (section_sp) {
2010 auto permissions = Flags(section_sp->GetPermissions());
2011 bool is_readonly = !permissions.Test(ePermissionsWritable) &&
2012 permissions.Test(ePermissionsReadable);
2013 if (is_readonly) {
2014 file_cache_bytes_read =
2015 ReadMemoryFromFileCache(resolved_addr, dst, dst_len, error);
2016 if (file_cache_bytes_read == dst_len)
2017 return file_cache_bytes_read;
2018 else if (file_cache_bytes_read > 0) {
2019 file_cache_read_buffer =
2020 std::make_unique<uint8_t[]>(file_cache_bytes_read);
2021 std::memcpy(file_cache_read_buffer.get(), dst, file_cache_bytes_read);
2027 if (ProcessIsValid()) {
2028 if (load_addr == LLDB_INVALID_ADDRESS)
2029 load_addr = resolved_addr.GetLoadAddress(this);
2031 if (load_addr == LLDB_INVALID_ADDRESS) {
2032 ModuleSP addr_module_sp(resolved_addr.GetModule());
2033 if (addr_module_sp && addr_module_sp->GetFileSpec())
2034 error = Status::FromErrorStringWithFormatv(
2035 "{0:F}[{1:x+}] can't be resolved, {0:F} is not currently loaded",
2036 addr_module_sp->GetFileSpec(), resolved_addr.GetFileAddress());
2037 else
2038 error = Status::FromErrorStringWithFormat(
2039 "0x%" PRIx64 " can't be resolved", resolved_addr.GetFileAddress());
2040 } else {
2041 bytes_read = m_process_sp->ReadMemory(load_addr, dst, dst_len, error);
2042 if (bytes_read != dst_len) {
2043 if (error.Success()) {
2044 if (bytes_read == 0)
2045 error = Status::FromErrorStringWithFormat(
2046 "read memory from 0x%" PRIx64 " failed", load_addr);
2047 else
2048 error = Status::FromErrorStringWithFormat(
2049 "only %" PRIu64 " of %" PRIu64
2050 " bytes were read from memory at 0x%" PRIx64,
2051 (uint64_t)bytes_read, (uint64_t)dst_len, load_addr);
2054 if (bytes_read) {
2055 if (load_addr_ptr)
2056 *load_addr_ptr = load_addr;
2057 return bytes_read;
2062 if (file_cache_read_buffer && file_cache_bytes_read > 0) {
2063 // Reading from the process failed. If we've previously succeeded in reading
2064 // something from the file cache, then copy that over and return that.
2065 std::memcpy(dst, file_cache_read_buffer.get(), file_cache_bytes_read);
2066 return file_cache_bytes_read;
2069 if (!file_cache_read_buffer && resolved_addr.IsSectionOffset()) {
2070 // If we didn't already try and read from the object file cache, then try
2071 // it after failing to read from the process.
2072 return ReadMemoryFromFileCache(resolved_addr, dst, dst_len, error);
2074 return 0;
2077 size_t Target::ReadCStringFromMemory(const Address &addr, std::string &out_str,
2078 Status &error, bool force_live_memory) {
2079 char buf[256];
2080 out_str.clear();
2081 addr_t curr_addr = addr.GetLoadAddress(this);
2082 Address address(addr);
2083 while (true) {
2084 size_t length = ReadCStringFromMemory(address, buf, sizeof(buf), error,
2085 force_live_memory);
2086 if (length == 0)
2087 break;
2088 out_str.append(buf, length);
2089 // If we got "length - 1" bytes, we didn't get the whole C string, we need
2090 // to read some more characters
2091 if (length == sizeof(buf) - 1)
2092 curr_addr += length;
2093 else
2094 break;
2095 address = Address(curr_addr);
2097 return out_str.size();
2100 size_t Target::ReadCStringFromMemory(const Address &addr, char *dst,
2101 size_t dst_max_len, Status &result_error,
2102 bool force_live_memory) {
2103 size_t total_cstr_len = 0;
2104 if (dst && dst_max_len) {
2105 result_error.Clear();
2106 // NULL out everything just to be safe
2107 memset(dst, 0, dst_max_len);
2108 addr_t curr_addr = addr.GetLoadAddress(this);
2109 Address address(addr);
2111 // We could call m_process_sp->GetMemoryCacheLineSize() but I don't think
2112 // this really needs to be tied to the memory cache subsystem's cache line
2113 // size, so leave this as a fixed constant.
2114 const size_t cache_line_size = 512;
2116 size_t bytes_left = dst_max_len - 1;
2117 char *curr_dst = dst;
2119 while (bytes_left > 0) {
2120 addr_t cache_line_bytes_left =
2121 cache_line_size - (curr_addr % cache_line_size);
2122 addr_t bytes_to_read =
2123 std::min<addr_t>(bytes_left, cache_line_bytes_left);
2124 Status error;
2125 size_t bytes_read = ReadMemory(address, curr_dst, bytes_to_read, error,
2126 force_live_memory);
2128 if (bytes_read == 0) {
2129 result_error = std::move(error);
2130 dst[total_cstr_len] = '\0';
2131 break;
2133 const size_t len = strlen(curr_dst);
2135 total_cstr_len += len;
2137 if (len < bytes_to_read)
2138 break;
2140 curr_dst += bytes_read;
2141 curr_addr += bytes_read;
2142 bytes_left -= bytes_read;
2143 address = Address(curr_addr);
2145 } else {
2146 if (dst == nullptr)
2147 result_error = Status::FromErrorString("invalid arguments");
2148 else
2149 result_error.Clear();
2151 return total_cstr_len;
2154 addr_t Target::GetReasonableReadSize(const Address &addr) {
2155 addr_t load_addr = addr.GetLoadAddress(this);
2156 if (load_addr != LLDB_INVALID_ADDRESS && m_process_sp) {
2157 // Avoid crossing cache line boundaries.
2158 addr_t cache_line_size = m_process_sp->GetMemoryCacheLineSize();
2159 return cache_line_size - (load_addr % cache_line_size);
2162 // The read is going to go to the file cache, so we can just pick a largish
2163 // value.
2164 return 0x1000;
2167 size_t Target::ReadStringFromMemory(const Address &addr, char *dst,
2168 size_t max_bytes, Status &error,
2169 size_t type_width, bool force_live_memory) {
2170 if (!dst || !max_bytes || !type_width || max_bytes < type_width)
2171 return 0;
2173 size_t total_bytes_read = 0;
2175 // Ensure a null terminator independent of the number of bytes that is
2176 // read.
2177 memset(dst, 0, max_bytes);
2178 size_t bytes_left = max_bytes - type_width;
2180 const char terminator[4] = {'\0', '\0', '\0', '\0'};
2181 assert(sizeof(terminator) >= type_width && "Attempting to validate a "
2182 "string with more than 4 bytes "
2183 "per character!");
2185 Address address = addr;
2186 char *curr_dst = dst;
2188 error.Clear();
2189 while (bytes_left > 0 && error.Success()) {
2190 addr_t bytes_to_read =
2191 std::min<addr_t>(bytes_left, GetReasonableReadSize(address));
2192 size_t bytes_read =
2193 ReadMemory(address, curr_dst, bytes_to_read, error, force_live_memory);
2195 if (bytes_read == 0)
2196 break;
2198 // Search for a null terminator of correct size and alignment in
2199 // bytes_read
2200 size_t aligned_start = total_bytes_read - total_bytes_read % type_width;
2201 for (size_t i = aligned_start;
2202 i + type_width <= total_bytes_read + bytes_read; i += type_width)
2203 if (::memcmp(&dst[i], terminator, type_width) == 0) {
2204 error.Clear();
2205 return i;
2208 total_bytes_read += bytes_read;
2209 curr_dst += bytes_read;
2210 address.Slide(bytes_read);
2211 bytes_left -= bytes_read;
2213 return total_bytes_read;
2216 size_t Target::ReadScalarIntegerFromMemory(const Address &addr, uint32_t byte_size,
2217 bool is_signed, Scalar &scalar,
2218 Status &error,
2219 bool force_live_memory) {
2220 uint64_t uval;
2222 if (byte_size <= sizeof(uval)) {
2223 size_t bytes_read =
2224 ReadMemory(addr, &uval, byte_size, error, force_live_memory);
2225 if (bytes_read == byte_size) {
2226 DataExtractor data(&uval, sizeof(uval), m_arch.GetSpec().GetByteOrder(),
2227 m_arch.GetSpec().GetAddressByteSize());
2228 lldb::offset_t offset = 0;
2229 if (byte_size <= 4)
2230 scalar = data.GetMaxU32(&offset, byte_size);
2231 else
2232 scalar = data.GetMaxU64(&offset, byte_size);
2234 if (is_signed)
2235 scalar.SignExtend(byte_size * 8);
2236 return bytes_read;
2238 } else {
2239 error = Status::FromErrorStringWithFormat(
2240 "byte size of %u is too large for integer scalar type", byte_size);
2242 return 0;
2245 uint64_t Target::ReadUnsignedIntegerFromMemory(const Address &addr,
2246 size_t integer_byte_size,
2247 uint64_t fail_value, Status &error,
2248 bool force_live_memory) {
2249 Scalar scalar;
2250 if (ReadScalarIntegerFromMemory(addr, integer_byte_size, false, scalar, error,
2251 force_live_memory))
2252 return scalar.ULongLong(fail_value);
2253 return fail_value;
2256 bool Target::ReadPointerFromMemory(const Address &addr, Status &error,
2257 Address &pointer_addr,
2258 bool force_live_memory) {
2259 Scalar scalar;
2260 if (ReadScalarIntegerFromMemory(addr, m_arch.GetSpec().GetAddressByteSize(),
2261 false, scalar, error, force_live_memory)) {
2262 addr_t pointer_vm_addr = scalar.ULongLong(LLDB_INVALID_ADDRESS);
2263 if (pointer_vm_addr != LLDB_INVALID_ADDRESS) {
2264 SectionLoadList &section_load_list = GetSectionLoadList();
2265 if (section_load_list.IsEmpty()) {
2266 // No sections are loaded, so we must assume we are not running yet and
2267 // anything we are given is a file address.
2268 m_images.ResolveFileAddress(pointer_vm_addr, pointer_addr);
2269 } else {
2270 // We have at least one section loaded. This can be because we have
2271 // manually loaded some sections with "target modules load ..." or
2272 // because we have a live process that has sections loaded through
2273 // the dynamic loader
2274 section_load_list.ResolveLoadAddress(pointer_vm_addr, pointer_addr);
2276 // We weren't able to resolve the pointer value, so just return an
2277 // address with no section
2278 if (!pointer_addr.IsValid())
2279 pointer_addr.SetOffset(pointer_vm_addr);
2280 return true;
2283 return false;
2286 ModuleSP Target::GetOrCreateModule(const ModuleSpec &orig_module_spec,
2287 bool notify, Status *error_ptr) {
2288 ModuleSP module_sp;
2290 Status error;
2292 // Apply any remappings specified in target.object-map:
2293 ModuleSpec module_spec(orig_module_spec);
2294 PathMappingList &obj_mapping = GetObjectPathMap();
2295 if (std::optional<FileSpec> remapped_obj_file =
2296 obj_mapping.RemapPath(orig_module_spec.GetFileSpec().GetPath(),
2297 true /* only_if_exists */)) {
2298 module_spec.GetFileSpec().SetPath(remapped_obj_file->GetPath());
2301 // First see if we already have this module in our module list. If we do,
2302 // then we're done, we don't need to consult the shared modules list. But
2303 // only do this if we are passed a UUID.
2305 if (module_spec.GetUUID().IsValid())
2306 module_sp = m_images.FindFirstModule(module_spec);
2308 if (!module_sp) {
2309 llvm::SmallVector<ModuleSP, 1>
2310 old_modules; // This will get filled in if we have a new version
2311 // of the library
2312 bool did_create_module = false;
2313 FileSpecList search_paths = GetExecutableSearchPaths();
2314 FileSpec symbol_file_spec;
2316 // Call locate module callback if set. This allows users to implement their
2317 // own module cache system. For example, to leverage build system artifacts,
2318 // to bypass pulling files from remote platform, or to search symbol files
2319 // from symbol servers.
2320 if (m_platform_sp)
2321 m_platform_sp->CallLocateModuleCallbackIfSet(
2322 module_spec, module_sp, symbol_file_spec, &did_create_module);
2324 // The result of this CallLocateModuleCallbackIfSet is one of the following.
2325 // 1. module_sp:loaded, symbol_file_spec:set
2326 // The callback found a module file and a symbol file for the
2327 // module_spec. We will call module_sp->SetSymbolFileFileSpec with
2328 // the symbol_file_spec later.
2329 // 2. module_sp:loaded, symbol_file_spec:empty
2330 // The callback only found a module file for the module_spec.
2331 // 3. module_sp:empty, symbol_file_spec:set
2332 // The callback only found a symbol file for the module. We continue
2333 // to find a module file for this module_spec and we will call
2334 // module_sp->SetSymbolFileFileSpec with the symbol_file_spec later.
2335 // 4. module_sp:empty, symbol_file_spec:empty
2336 // Platform does not exist, the callback is not set, the callback did
2337 // not find any module files nor any symbol files, the callback failed,
2338 // or something went wrong. We continue to find a module file for this
2339 // module_spec.
2341 if (!module_sp) {
2342 // If there are image search path entries, try to use them to acquire a
2343 // suitable image.
2344 if (m_image_search_paths.GetSize()) {
2345 ModuleSpec transformed_spec(module_spec);
2346 ConstString transformed_dir;
2347 if (m_image_search_paths.RemapPath(
2348 module_spec.GetFileSpec().GetDirectory(), transformed_dir)) {
2349 transformed_spec.GetFileSpec().SetDirectory(transformed_dir);
2350 transformed_spec.GetFileSpec().SetFilename(
2351 module_spec.GetFileSpec().GetFilename());
2352 error = ModuleList::GetSharedModule(transformed_spec, module_sp,
2353 &search_paths, &old_modules,
2354 &did_create_module);
2359 if (!module_sp) {
2360 // If we have a UUID, we can check our global shared module list in case
2361 // we already have it. If we don't have a valid UUID, then we can't since
2362 // the path in "module_spec" will be a platform path, and we will need to
2363 // let the platform find that file. For example, we could be asking for
2364 // "/usr/lib/dyld" and if we do not have a UUID, we don't want to pick
2365 // the local copy of "/usr/lib/dyld" since our platform could be a remote
2366 // platform that has its own "/usr/lib/dyld" in an SDK or in a local file
2367 // cache.
2368 if (module_spec.GetUUID().IsValid()) {
2369 // We have a UUID, it is OK to check the global module list...
2370 error =
2371 ModuleList::GetSharedModule(module_spec, module_sp, &search_paths,
2372 &old_modules, &did_create_module);
2375 if (!module_sp) {
2376 // The platform is responsible for finding and caching an appropriate
2377 // module in the shared module cache.
2378 if (m_platform_sp) {
2379 error = m_platform_sp->GetSharedModule(
2380 module_spec, m_process_sp.get(), module_sp, &search_paths,
2381 &old_modules, &did_create_module);
2382 } else {
2383 error = Status::FromErrorString("no platform is currently set");
2388 // We found a module that wasn't in our target list. Let's make sure that
2389 // there wasn't an equivalent module in the list already, and if there was,
2390 // let's remove it.
2391 if (module_sp) {
2392 ObjectFile *objfile = module_sp->GetObjectFile();
2393 if (objfile) {
2394 switch (objfile->GetType()) {
2395 case ObjectFile::eTypeCoreFile: /// A core file that has a checkpoint of
2396 /// a program's execution state
2397 case ObjectFile::eTypeExecutable: /// A normal executable
2398 case ObjectFile::eTypeDynamicLinker: /// The platform's dynamic linker
2399 /// executable
2400 case ObjectFile::eTypeObjectFile: /// An intermediate object file
2401 case ObjectFile::eTypeSharedLibrary: /// A shared library that can be
2402 /// used during execution
2403 break;
2404 case ObjectFile::eTypeDebugInfo: /// An object file that contains only
2405 /// debug information
2406 if (error_ptr)
2407 *error_ptr = Status::FromErrorString(
2408 "debug info files aren't valid target "
2409 "modules, please specify an executable");
2410 return ModuleSP();
2411 case ObjectFile::eTypeStubLibrary: /// A library that can be linked
2412 /// against but not used for
2413 /// execution
2414 if (error_ptr)
2415 *error_ptr = Status::FromErrorString(
2416 "stub libraries aren't valid target "
2417 "modules, please specify an executable");
2418 return ModuleSP();
2419 default:
2420 if (error_ptr)
2421 *error_ptr = Status::FromErrorString(
2422 "unsupported file type, please specify an executable");
2423 return ModuleSP();
2425 // GetSharedModule is not guaranteed to find the old shared module, for
2426 // instance in the common case where you pass in the UUID, it is only
2427 // going to find the one module matching the UUID. In fact, it has no
2428 // good way to know what the "old module" relevant to this target is,
2429 // since there might be many copies of a module with this file spec in
2430 // various running debug sessions, but only one of them will belong to
2431 // this target. So let's remove the UUID from the module list, and look
2432 // in the target's module list. Only do this if there is SOMETHING else
2433 // in the module spec...
2434 if (module_spec.GetUUID().IsValid() &&
2435 !module_spec.GetFileSpec().GetFilename().IsEmpty() &&
2436 !module_spec.GetFileSpec().GetDirectory().IsEmpty()) {
2437 ModuleSpec module_spec_copy(module_spec.GetFileSpec());
2438 module_spec_copy.GetUUID().Clear();
2440 ModuleList found_modules;
2441 m_images.FindModules(module_spec_copy, found_modules);
2442 found_modules.ForEach([&](const ModuleSP &found_module) -> bool {
2443 old_modules.push_back(found_module);
2444 return true;
2448 // If the locate module callback had found a symbol file, set it to the
2449 // module_sp before preloading symbols.
2450 if (symbol_file_spec)
2451 module_sp->SetSymbolFileFileSpec(symbol_file_spec);
2453 // Preload symbols outside of any lock, so hopefully we can do this for
2454 // each library in parallel.
2455 if (GetPreloadSymbols())
2456 module_sp->PreloadSymbols();
2457 llvm::SmallVector<ModuleSP, 1> replaced_modules;
2458 for (ModuleSP &old_module_sp : old_modules) {
2459 if (m_images.GetIndexForModule(old_module_sp.get()) !=
2460 LLDB_INVALID_INDEX32) {
2461 if (replaced_modules.empty())
2462 m_images.ReplaceModule(old_module_sp, module_sp);
2463 else
2464 m_images.Remove(old_module_sp);
2466 replaced_modules.push_back(std::move(old_module_sp));
2470 if (replaced_modules.size() > 1) {
2471 // The same new module replaced multiple old modules
2472 // simultaneously. It's not clear this should ever
2473 // happen (if we always replace old modules as we add
2474 // new ones, presumably we should never have more than
2475 // one old one). If there are legitimate cases where
2476 // this happens, then the ModuleList::Notifier interface
2477 // may need to be adjusted to allow reporting this.
2478 // In the meantime, just log that this has happened; just
2479 // above we called ReplaceModule on the first one, and Remove
2480 // on the rest.
2481 if (Log *log = GetLog(LLDBLog::Target | LLDBLog::Modules)) {
2482 StreamString message;
2483 auto dump = [&message](Module &dump_module) -> void {
2484 UUID dump_uuid = dump_module.GetUUID();
2486 message << '[';
2487 dump_module.GetDescription(message.AsRawOstream());
2488 message << " (uuid ";
2490 if (dump_uuid.IsValid())
2491 dump_uuid.Dump(message);
2492 else
2493 message << "not specified";
2495 message << ")]";
2498 message << "New module ";
2499 dump(*module_sp);
2500 message.AsRawOstream()
2501 << llvm::formatv(" simultaneously replaced {0} old modules: ",
2502 replaced_modules.size());
2503 for (ModuleSP &replaced_module_sp : replaced_modules)
2504 dump(*replaced_module_sp);
2506 log->PutString(message.GetString());
2510 if (replaced_modules.empty())
2511 m_images.Append(module_sp, notify);
2513 for (ModuleSP &old_module_sp : replaced_modules) {
2514 Module *old_module_ptr = old_module_sp.get();
2515 old_module_sp.reset();
2516 ModuleList::RemoveSharedModuleIfOrphaned(old_module_ptr);
2518 } else
2519 module_sp.reset();
2522 if (error_ptr)
2523 *error_ptr = std::move(error);
2524 return module_sp;
2527 TargetSP Target::CalculateTarget() { return shared_from_this(); }
2529 ProcessSP Target::CalculateProcess() { return m_process_sp; }
2531 ThreadSP Target::CalculateThread() { return ThreadSP(); }
2533 StackFrameSP Target::CalculateStackFrame() { return StackFrameSP(); }
2535 void Target::CalculateExecutionContext(ExecutionContext &exe_ctx) {
2536 exe_ctx.Clear();
2537 exe_ctx.SetTargetPtr(this);
2540 PathMappingList &Target::GetImageSearchPathList() {
2541 return m_image_search_paths;
2544 void Target::ImageSearchPathsChanged(const PathMappingList &path_list,
2545 void *baton) {
2546 Target *target = (Target *)baton;
2547 ModuleSP exe_module_sp(target->GetExecutableModule());
2548 if (exe_module_sp)
2549 target->SetExecutableModule(exe_module_sp, eLoadDependentsYes);
2552 llvm::Expected<lldb::TypeSystemSP>
2553 Target::GetScratchTypeSystemForLanguage(lldb::LanguageType language,
2554 bool create_on_demand) {
2555 if (!m_valid)
2556 return llvm::createStringError("Invalid Target");
2558 if (language == eLanguageTypeMipsAssembler // GNU AS and LLVM use it for all
2559 // assembly code
2560 || language == eLanguageTypeUnknown) {
2561 LanguageSet languages_for_expressions =
2562 Language::GetLanguagesSupportingTypeSystemsForExpressions();
2564 if (languages_for_expressions[eLanguageTypeC]) {
2565 language = eLanguageTypeC; // LLDB's default. Override by setting the
2566 // target language.
2567 } else {
2568 if (languages_for_expressions.Empty())
2569 return llvm::createStringError(
2570 "No expression support for any languages");
2571 language = (LanguageType)languages_for_expressions.bitvector.find_first();
2575 return m_scratch_type_system_map.GetTypeSystemForLanguage(language, this,
2576 create_on_demand);
2579 CompilerType Target::GetRegisterType(const std::string &name,
2580 const lldb_private::RegisterFlags &flags,
2581 uint32_t byte_size) {
2582 RegisterTypeBuilderSP provider = PluginManager::GetRegisterTypeBuilder(*this);
2583 assert(provider);
2584 return provider->GetRegisterType(name, flags, byte_size);
2587 std::vector<lldb::TypeSystemSP>
2588 Target::GetScratchTypeSystems(bool create_on_demand) {
2589 if (!m_valid)
2590 return {};
2592 // Some TypeSystem instances are associated with several LanguageTypes so
2593 // they will show up several times in the loop below. The SetVector filters
2594 // out all duplicates as they serve no use for the caller.
2595 std::vector<lldb::TypeSystemSP> scratch_type_systems;
2597 LanguageSet languages_for_expressions =
2598 Language::GetLanguagesSupportingTypeSystemsForExpressions();
2600 for (auto bit : languages_for_expressions.bitvector.set_bits()) {
2601 auto language = (LanguageType)bit;
2602 auto type_system_or_err =
2603 GetScratchTypeSystemForLanguage(language, create_on_demand);
2604 if (!type_system_or_err)
2605 LLDB_LOG_ERROR(
2606 GetLog(LLDBLog::Target), type_system_or_err.takeError(),
2607 "Language '{1}' has expression support but no scratch type "
2608 "system available: {0}",
2609 Language::GetNameForLanguageType(language));
2610 else
2611 if (auto ts = *type_system_or_err)
2612 scratch_type_systems.push_back(ts);
2615 std::sort(scratch_type_systems.begin(), scratch_type_systems.end());
2616 scratch_type_systems.erase(
2617 std::unique(scratch_type_systems.begin(), scratch_type_systems.end()),
2618 scratch_type_systems.end());
2619 return scratch_type_systems;
2622 PersistentExpressionState *
2623 Target::GetPersistentExpressionStateForLanguage(lldb::LanguageType language) {
2624 auto type_system_or_err = GetScratchTypeSystemForLanguage(language, true);
2626 if (auto err = type_system_or_err.takeError()) {
2627 LLDB_LOG_ERROR(
2628 GetLog(LLDBLog::Target), std::move(err),
2629 "Unable to get persistent expression state for language {1}: {0}",
2630 Language::GetNameForLanguageType(language));
2631 return nullptr;
2634 if (auto ts = *type_system_or_err)
2635 return ts->GetPersistentExpressionState();
2637 LLDB_LOG(GetLog(LLDBLog::Target),
2638 "Unable to get persistent expression state for language {1}: {0}",
2639 Language::GetNameForLanguageType(language));
2640 return nullptr;
2643 UserExpression *Target::GetUserExpressionForLanguage(
2644 llvm::StringRef expr, llvm::StringRef prefix, SourceLanguage language,
2645 Expression::ResultType desired_type,
2646 const EvaluateExpressionOptions &options, ValueObject *ctx_obj,
2647 Status &error) {
2648 auto type_system_or_err =
2649 GetScratchTypeSystemForLanguage(language.AsLanguageType());
2650 if (auto err = type_system_or_err.takeError()) {
2651 error = Status::FromErrorStringWithFormat(
2652 "Could not find type system for language %s: %s",
2653 Language::GetNameForLanguageType(language.AsLanguageType()),
2654 llvm::toString(std::move(err)).c_str());
2655 return nullptr;
2658 auto ts = *type_system_or_err;
2659 if (!ts) {
2660 error = Status::FromErrorStringWithFormat(
2661 "Type system for language %s is no longer live",
2662 language.GetDescription().data());
2663 return nullptr;
2666 auto *user_expr = ts->GetUserExpression(expr, prefix, language, desired_type,
2667 options, ctx_obj);
2668 if (!user_expr)
2669 error = Status::FromErrorStringWithFormat(
2670 "Could not create an expression for language %s",
2671 language.GetDescription().data());
2673 return user_expr;
2676 FunctionCaller *Target::GetFunctionCallerForLanguage(
2677 lldb::LanguageType language, const CompilerType &return_type,
2678 const Address &function_address, const ValueList &arg_value_list,
2679 const char *name, Status &error) {
2680 auto type_system_or_err = GetScratchTypeSystemForLanguage(language);
2681 if (auto err = type_system_or_err.takeError()) {
2682 error = Status::FromErrorStringWithFormat(
2683 "Could not find type system for language %s: %s",
2684 Language::GetNameForLanguageType(language),
2685 llvm::toString(std::move(err)).c_str());
2686 return nullptr;
2688 auto ts = *type_system_or_err;
2689 if (!ts) {
2690 error = Status::FromErrorStringWithFormat(
2691 "Type system for language %s is no longer live",
2692 Language::GetNameForLanguageType(language));
2693 return nullptr;
2695 auto *persistent_fn = ts->GetFunctionCaller(return_type, function_address,
2696 arg_value_list, name);
2697 if (!persistent_fn)
2698 error = Status::FromErrorStringWithFormat(
2699 "Could not create an expression for language %s",
2700 Language::GetNameForLanguageType(language));
2702 return persistent_fn;
2705 llvm::Expected<std::unique_ptr<UtilityFunction>>
2706 Target::CreateUtilityFunction(std::string expression, std::string name,
2707 lldb::LanguageType language,
2708 ExecutionContext &exe_ctx) {
2709 auto type_system_or_err = GetScratchTypeSystemForLanguage(language);
2710 if (!type_system_or_err)
2711 return type_system_or_err.takeError();
2712 auto ts = *type_system_or_err;
2713 if (!ts)
2714 return llvm::createStringError(
2715 llvm::StringRef("Type system for language ") +
2716 Language::GetNameForLanguageType(language) +
2717 llvm::StringRef(" is no longer live"));
2718 std::unique_ptr<UtilityFunction> utility_fn =
2719 ts->CreateUtilityFunction(std::move(expression), std::move(name));
2720 if (!utility_fn)
2721 return llvm::createStringError(
2722 llvm::StringRef("Could not create an expression for language") +
2723 Language::GetNameForLanguageType(language));
2725 DiagnosticManager diagnostics;
2726 if (!utility_fn->Install(diagnostics, exe_ctx))
2727 return diagnostics.GetAsError(lldb::eExpressionSetupError,
2728 "Could not install utility function:");
2730 return std::move(utility_fn);
2733 void Target::SettingsInitialize() { Process::SettingsInitialize(); }
2735 void Target::SettingsTerminate() { Process::SettingsTerminate(); }
2737 FileSpecList Target::GetDefaultExecutableSearchPaths() {
2738 return Target::GetGlobalProperties().GetExecutableSearchPaths();
2741 FileSpecList Target::GetDefaultDebugFileSearchPaths() {
2742 return Target::GetGlobalProperties().GetDebugFileSearchPaths();
2745 ArchSpec Target::GetDefaultArchitecture() {
2746 return Target::GetGlobalProperties().GetDefaultArchitecture();
2749 void Target::SetDefaultArchitecture(const ArchSpec &arch) {
2750 LLDB_LOG(GetLog(LLDBLog::Target),
2751 "setting target's default architecture to {0} ({1})",
2752 arch.GetArchitectureName(), arch.GetTriple().getTriple());
2753 Target::GetGlobalProperties().SetDefaultArchitecture(arch);
2756 llvm::Error Target::SetLabel(llvm::StringRef label) {
2757 size_t n = LLDB_INVALID_INDEX32;
2758 if (llvm::to_integer(label, n))
2759 return llvm::createStringError("Cannot use integer as target label.");
2760 TargetList &targets = GetDebugger().GetTargetList();
2761 for (size_t i = 0; i < targets.GetNumTargets(); i++) {
2762 TargetSP target_sp = targets.GetTargetAtIndex(i);
2763 if (target_sp && target_sp->GetLabel() == label) {
2764 return llvm::make_error<llvm::StringError>(
2765 llvm::formatv(
2766 "Cannot use label '{0}' since it's set in target #{1}.", label,
2768 llvm::inconvertibleErrorCode());
2772 m_label = label.str();
2773 return llvm::Error::success();
2776 Target *Target::GetTargetFromContexts(const ExecutionContext *exe_ctx_ptr,
2777 const SymbolContext *sc_ptr) {
2778 // The target can either exist in the "process" of ExecutionContext, or in
2779 // the "target_sp" member of SymbolContext. This accessor helper function
2780 // will get the target from one of these locations.
2782 Target *target = nullptr;
2783 if (sc_ptr != nullptr)
2784 target = sc_ptr->target_sp.get();
2785 if (target == nullptr && exe_ctx_ptr)
2786 target = exe_ctx_ptr->GetTargetPtr();
2787 return target;
2790 ExpressionResults Target::EvaluateExpression(
2791 llvm::StringRef expr, ExecutionContextScope *exe_scope,
2792 lldb::ValueObjectSP &result_valobj_sp,
2793 const EvaluateExpressionOptions &options, std::string *fixed_expression,
2794 ValueObject *ctx_obj) {
2795 result_valobj_sp.reset();
2797 ExpressionResults execution_results = eExpressionSetupError;
2799 if (expr.empty()) {
2800 m_stats.GetExpressionStats().NotifyFailure();
2801 return execution_results;
2804 // We shouldn't run stop hooks in expressions.
2805 bool old_suppress_value = m_suppress_stop_hooks;
2806 m_suppress_stop_hooks = true;
2807 auto on_exit = llvm::make_scope_exit([this, old_suppress_value]() {
2808 m_suppress_stop_hooks = old_suppress_value;
2811 ExecutionContext exe_ctx;
2813 if (exe_scope) {
2814 exe_scope->CalculateExecutionContext(exe_ctx);
2815 } else if (m_process_sp) {
2816 m_process_sp->CalculateExecutionContext(exe_ctx);
2817 } else {
2818 CalculateExecutionContext(exe_ctx);
2821 // Make sure we aren't just trying to see the value of a persistent variable
2822 // (something like "$0")
2823 // Only check for persistent variables the expression starts with a '$'
2824 lldb::ExpressionVariableSP persistent_var_sp;
2825 if (expr[0] == '$') {
2826 auto type_system_or_err =
2827 GetScratchTypeSystemForLanguage(eLanguageTypeC);
2828 if (auto err = type_system_or_err.takeError()) {
2829 LLDB_LOG_ERROR(GetLog(LLDBLog::Target), std::move(err),
2830 "Unable to get scratch type system");
2831 } else {
2832 auto ts = *type_system_or_err;
2833 if (!ts)
2834 LLDB_LOG_ERROR(GetLog(LLDBLog::Target), std::move(err),
2835 "Scratch type system is no longer live: {0}");
2836 else
2837 persistent_var_sp =
2838 ts->GetPersistentExpressionState()->GetVariable(expr);
2841 if (persistent_var_sp) {
2842 result_valobj_sp = persistent_var_sp->GetValueObject();
2843 execution_results = eExpressionCompleted;
2844 } else {
2845 llvm::StringRef prefix = GetExpressionPrefixContents();
2846 execution_results =
2847 UserExpression::Evaluate(exe_ctx, options, expr, prefix,
2848 result_valobj_sp, fixed_expression, ctx_obj);
2851 if (execution_results == eExpressionCompleted)
2852 m_stats.GetExpressionStats().NotifySuccess();
2853 else
2854 m_stats.GetExpressionStats().NotifyFailure();
2855 return execution_results;
2858 lldb::ExpressionVariableSP Target::GetPersistentVariable(ConstString name) {
2859 lldb::ExpressionVariableSP variable_sp;
2860 m_scratch_type_system_map.ForEach(
2861 [name, &variable_sp](TypeSystemSP type_system) -> bool {
2862 auto ts = type_system.get();
2863 if (!ts)
2864 return true;
2865 if (PersistentExpressionState *persistent_state =
2866 ts->GetPersistentExpressionState()) {
2867 variable_sp = persistent_state->GetVariable(name);
2869 if (variable_sp)
2870 return false; // Stop iterating the ForEach
2872 return true; // Keep iterating the ForEach
2874 return variable_sp;
2877 lldb::addr_t Target::GetPersistentSymbol(ConstString name) {
2878 lldb::addr_t address = LLDB_INVALID_ADDRESS;
2880 m_scratch_type_system_map.ForEach(
2881 [name, &address](lldb::TypeSystemSP type_system) -> bool {
2882 auto ts = type_system.get();
2883 if (!ts)
2884 return true;
2886 if (PersistentExpressionState *persistent_state =
2887 ts->GetPersistentExpressionState()) {
2888 address = persistent_state->LookupSymbol(name);
2889 if (address != LLDB_INVALID_ADDRESS)
2890 return false; // Stop iterating the ForEach
2892 return true; // Keep iterating the ForEach
2894 return address;
2897 llvm::Expected<lldb_private::Address> Target::GetEntryPointAddress() {
2898 Module *exe_module = GetExecutableModulePointer();
2900 // Try to find the entry point address in the primary executable.
2901 const bool has_primary_executable = exe_module && exe_module->GetObjectFile();
2902 if (has_primary_executable) {
2903 Address entry_addr = exe_module->GetObjectFile()->GetEntryPointAddress();
2904 if (entry_addr.IsValid())
2905 return entry_addr;
2908 const ModuleList &modules = GetImages();
2909 const size_t num_images = modules.GetSize();
2910 for (size_t idx = 0; idx < num_images; ++idx) {
2911 ModuleSP module_sp(modules.GetModuleAtIndex(idx));
2912 if (!module_sp || !module_sp->GetObjectFile())
2913 continue;
2915 Address entry_addr = module_sp->GetObjectFile()->GetEntryPointAddress();
2916 if (entry_addr.IsValid())
2917 return entry_addr;
2920 // We haven't found the entry point address. Return an appropriate error.
2921 if (!has_primary_executable)
2922 return llvm::createStringError(
2923 "No primary executable found and could not find entry point address in "
2924 "any executable module");
2926 return llvm::createStringError(
2927 "Could not find entry point address for primary executable module \"" +
2928 exe_module->GetFileSpec().GetFilename().GetStringRef() + "\"");
2931 lldb::addr_t Target::GetCallableLoadAddress(lldb::addr_t load_addr,
2932 AddressClass addr_class) const {
2933 auto arch_plugin = GetArchitecturePlugin();
2934 return arch_plugin
2935 ? arch_plugin->GetCallableLoadAddress(load_addr, addr_class)
2936 : load_addr;
2939 lldb::addr_t Target::GetOpcodeLoadAddress(lldb::addr_t load_addr,
2940 AddressClass addr_class) const {
2941 auto arch_plugin = GetArchitecturePlugin();
2942 return arch_plugin ? arch_plugin->GetOpcodeLoadAddress(load_addr, addr_class)
2943 : load_addr;
2946 lldb::addr_t Target::GetBreakableLoadAddress(lldb::addr_t addr) {
2947 auto arch_plugin = GetArchitecturePlugin();
2948 return arch_plugin ? arch_plugin->GetBreakableLoadAddress(addr, *this) : addr;
2951 SourceManager &Target::GetSourceManager() {
2952 if (!m_source_manager_up)
2953 m_source_manager_up = std::make_unique<SourceManager>(shared_from_this());
2954 return *m_source_manager_up;
2957 Target::StopHookSP Target::CreateStopHook(StopHook::StopHookKind kind) {
2958 lldb::user_id_t new_uid = ++m_stop_hook_next_id;
2959 Target::StopHookSP stop_hook_sp;
2960 switch (kind) {
2961 case StopHook::StopHookKind::CommandBased:
2962 stop_hook_sp.reset(new StopHookCommandLine(shared_from_this(), new_uid));
2963 break;
2964 case StopHook::StopHookKind::ScriptBased:
2965 stop_hook_sp.reset(new StopHookScripted(shared_from_this(), new_uid));
2966 break;
2968 m_stop_hooks[new_uid] = stop_hook_sp;
2969 return stop_hook_sp;
2972 void Target::UndoCreateStopHook(lldb::user_id_t user_id) {
2973 if (!RemoveStopHookByID(user_id))
2974 return;
2975 if (user_id == m_stop_hook_next_id)
2976 m_stop_hook_next_id--;
2979 bool Target::RemoveStopHookByID(lldb::user_id_t user_id) {
2980 size_t num_removed = m_stop_hooks.erase(user_id);
2981 return (num_removed != 0);
2984 void Target::RemoveAllStopHooks() { m_stop_hooks.clear(); }
2986 Target::StopHookSP Target::GetStopHookByID(lldb::user_id_t user_id) {
2987 StopHookSP found_hook;
2989 StopHookCollection::iterator specified_hook_iter;
2990 specified_hook_iter = m_stop_hooks.find(user_id);
2991 if (specified_hook_iter != m_stop_hooks.end())
2992 found_hook = (*specified_hook_iter).second;
2993 return found_hook;
2996 bool Target::SetStopHookActiveStateByID(lldb::user_id_t user_id,
2997 bool active_state) {
2998 StopHookCollection::iterator specified_hook_iter;
2999 specified_hook_iter = m_stop_hooks.find(user_id);
3000 if (specified_hook_iter == m_stop_hooks.end())
3001 return false;
3003 (*specified_hook_iter).second->SetIsActive(active_state);
3004 return true;
3007 void Target::SetAllStopHooksActiveState(bool active_state) {
3008 StopHookCollection::iterator pos, end = m_stop_hooks.end();
3009 for (pos = m_stop_hooks.begin(); pos != end; pos++) {
3010 (*pos).second->SetIsActive(active_state);
3014 bool Target::RunStopHooks() {
3015 if (m_suppress_stop_hooks)
3016 return false;
3018 if (!m_process_sp)
3019 return false;
3021 // Somebody might have restarted the process:
3022 // Still return false, the return value is about US restarting the target.
3023 if (m_process_sp->GetState() != eStateStopped)
3024 return false;
3026 if (m_stop_hooks.empty())
3027 return false;
3029 // If there aren't any active stop hooks, don't bother either.
3030 bool any_active_hooks = false;
3031 for (auto hook : m_stop_hooks) {
3032 if (hook.second->IsActive()) {
3033 any_active_hooks = true;
3034 break;
3037 if (!any_active_hooks)
3038 return false;
3040 // Make sure we check that we are not stopped because of us running a user
3041 // expression since in that case we do not want to run the stop-hooks. Note,
3042 // you can't just check whether the last stop was for a User Expression,
3043 // because breakpoint commands get run before stop hooks, and one of them
3044 // might have run an expression. You have to ensure you run the stop hooks
3045 // once per natural stop.
3046 uint32_t last_natural_stop = m_process_sp->GetModIDRef().GetLastNaturalStopID();
3047 if (last_natural_stop != 0 && m_latest_stop_hook_id == last_natural_stop)
3048 return false;
3050 m_latest_stop_hook_id = last_natural_stop;
3052 std::vector<ExecutionContext> exc_ctx_with_reasons;
3054 ThreadList &cur_threadlist = m_process_sp->GetThreadList();
3055 size_t num_threads = cur_threadlist.GetSize();
3056 for (size_t i = 0; i < num_threads; i++) {
3057 lldb::ThreadSP cur_thread_sp = cur_threadlist.GetThreadAtIndex(i);
3058 if (cur_thread_sp->ThreadStoppedForAReason()) {
3059 lldb::StackFrameSP cur_frame_sp = cur_thread_sp->GetStackFrameAtIndex(0);
3060 exc_ctx_with_reasons.emplace_back(m_process_sp.get(), cur_thread_sp.get(),
3061 cur_frame_sp.get());
3065 // If no threads stopped for a reason, don't run the stop-hooks.
3066 size_t num_exe_ctx = exc_ctx_with_reasons.size();
3067 if (num_exe_ctx == 0)
3068 return false;
3070 StreamSP output_sp = m_debugger.GetAsyncOutputStream();
3072 bool auto_continue = false;
3073 bool hooks_ran = false;
3074 bool print_hook_header = (m_stop_hooks.size() != 1);
3075 bool print_thread_header = (num_exe_ctx != 1);
3076 bool should_stop = false;
3077 bool somebody_restarted = false;
3079 for (auto stop_entry : m_stop_hooks) {
3080 StopHookSP cur_hook_sp = stop_entry.second;
3081 if (!cur_hook_sp->IsActive())
3082 continue;
3084 bool any_thread_matched = false;
3085 for (auto exc_ctx : exc_ctx_with_reasons) {
3086 // We detect somebody restarted in the stop-hook loop, and broke out of
3087 // that loop back to here. So break out of here too.
3088 if (somebody_restarted)
3089 break;
3091 if (!cur_hook_sp->ExecutionContextPasses(exc_ctx))
3092 continue;
3094 // We only consult the auto-continue for a stop hook if it matched the
3095 // specifier.
3096 auto_continue |= cur_hook_sp->GetAutoContinue();
3098 if (!hooks_ran)
3099 hooks_ran = true;
3101 if (print_hook_header && !any_thread_matched) {
3102 StreamString s;
3103 cur_hook_sp->GetDescription(s, eDescriptionLevelBrief);
3104 if (s.GetSize() != 0)
3105 output_sp->Printf("\n- Hook %" PRIu64 " (%s)\n", cur_hook_sp->GetID(),
3106 s.GetData());
3107 else
3108 output_sp->Printf("\n- Hook %" PRIu64 "\n", cur_hook_sp->GetID());
3109 any_thread_matched = true;
3112 if (print_thread_header)
3113 output_sp->Printf("-- Thread %d\n",
3114 exc_ctx.GetThreadPtr()->GetIndexID());
3116 StopHook::StopHookResult this_result =
3117 cur_hook_sp->HandleStop(exc_ctx, output_sp);
3118 bool this_should_stop = true;
3120 switch (this_result) {
3121 case StopHook::StopHookResult::KeepStopped:
3122 // If this hook is set to auto-continue that should override the
3123 // HandleStop result...
3124 if (cur_hook_sp->GetAutoContinue())
3125 this_should_stop = false;
3126 else
3127 this_should_stop = true;
3129 break;
3130 case StopHook::StopHookResult::RequestContinue:
3131 this_should_stop = false;
3132 break;
3133 case StopHook::StopHookResult::AlreadyContinued:
3134 // We don't have a good way to prohibit people from restarting the
3135 // target willy nilly in a stop hook. If the hook did so, give a
3136 // gentle suggestion here and bag out if the hook processing.
3137 output_sp->Printf("\nAborting stop hooks, hook %" PRIu64
3138 " set the program running.\n"
3139 " Consider using '-G true' to make "
3140 "stop hooks auto-continue.\n",
3141 cur_hook_sp->GetID());
3142 somebody_restarted = true;
3143 break;
3145 // If we're already restarted, stop processing stop hooks.
3146 // FIXME: if we are doing non-stop mode for real, we would have to
3147 // check that OUR thread was restarted, otherwise we should keep
3148 // processing stop hooks.
3149 if (somebody_restarted)
3150 break;
3152 // If anybody wanted to stop, we should all stop.
3153 if (!should_stop)
3154 should_stop = this_should_stop;
3158 output_sp->Flush();
3160 // If one of the commands in the stop hook already restarted the target,
3161 // report that fact.
3162 if (somebody_restarted)
3163 return true;
3165 // Finally, if auto-continue was requested, do it now:
3166 // We only compute should_stop against the hook results if a hook got to run
3167 // which is why we have to do this conjoint test.
3168 if ((hooks_ran && !should_stop) || auto_continue) {
3169 Log *log = GetLog(LLDBLog::Process);
3170 Status error = m_process_sp->PrivateResume();
3171 if (error.Success()) {
3172 LLDB_LOG(log, "Resuming from RunStopHooks");
3173 return true;
3174 } else {
3175 LLDB_LOG(log, "Resuming from RunStopHooks failed: {0}", error);
3176 return false;
3180 return false;
3183 TargetProperties &Target::GetGlobalProperties() {
3184 // NOTE: intentional leak so we don't crash if global destructor chain gets
3185 // called as other threads still use the result of this function
3186 static TargetProperties *g_settings_ptr =
3187 new TargetProperties(nullptr);
3188 return *g_settings_ptr;
3191 Status Target::Install(ProcessLaunchInfo *launch_info) {
3192 Status error;
3193 PlatformSP platform_sp(GetPlatform());
3194 if (!platform_sp || !platform_sp->IsRemote() || !platform_sp->IsConnected())
3195 return error;
3197 // Install all files that have an install path when connected to a
3198 // remote platform. If target.auto-install-main-executable is set then
3199 // also install the main executable even if it does not have an explicit
3200 // install path specified.
3202 for (auto module_sp : GetImages().Modules()) {
3203 if (module_sp == GetExecutableModule()) {
3204 MainExecutableInstaller installer{platform_sp, module_sp,
3205 shared_from_this(), *launch_info};
3206 error = installExecutable(installer);
3207 } else {
3208 ExecutableInstaller installer{platform_sp, module_sp};
3209 error = installExecutable(installer);
3212 if (error.Fail())
3213 return error;
3216 return error;
3219 bool Target::ResolveLoadAddress(addr_t load_addr, Address &so_addr,
3220 uint32_t stop_id) {
3221 return m_section_load_history.ResolveLoadAddress(stop_id, load_addr, so_addr);
3224 bool Target::ResolveFileAddress(lldb::addr_t file_addr,
3225 Address &resolved_addr) {
3226 return m_images.ResolveFileAddress(file_addr, resolved_addr);
3229 bool Target::SetSectionLoadAddress(const SectionSP &section_sp,
3230 addr_t new_section_load_addr,
3231 bool warn_multiple) {
3232 const addr_t old_section_load_addr =
3233 m_section_load_history.GetSectionLoadAddress(
3234 SectionLoadHistory::eStopIDNow, section_sp);
3235 if (old_section_load_addr != new_section_load_addr) {
3236 uint32_t stop_id = 0;
3237 ProcessSP process_sp(GetProcessSP());
3238 if (process_sp)
3239 stop_id = process_sp->GetStopID();
3240 else
3241 stop_id = m_section_load_history.GetLastStopID();
3242 if (m_section_load_history.SetSectionLoadAddress(
3243 stop_id, section_sp, new_section_load_addr, warn_multiple))
3244 return true; // Return true if the section load address was changed...
3246 return false; // Return false to indicate nothing changed
3249 size_t Target::UnloadModuleSections(const ModuleList &module_list) {
3250 size_t section_unload_count = 0;
3251 size_t num_modules = module_list.GetSize();
3252 for (size_t i = 0; i < num_modules; ++i) {
3253 section_unload_count +=
3254 UnloadModuleSections(module_list.GetModuleAtIndex(i));
3256 return section_unload_count;
3259 size_t Target::UnloadModuleSections(const lldb::ModuleSP &module_sp) {
3260 uint32_t stop_id = 0;
3261 ProcessSP process_sp(GetProcessSP());
3262 if (process_sp)
3263 stop_id = process_sp->GetStopID();
3264 else
3265 stop_id = m_section_load_history.GetLastStopID();
3266 SectionList *sections = module_sp->GetSectionList();
3267 size_t section_unload_count = 0;
3268 if (sections) {
3269 const uint32_t num_sections = sections->GetNumSections(0);
3270 for (uint32_t i = 0; i < num_sections; ++i) {
3271 section_unload_count += m_section_load_history.SetSectionUnloaded(
3272 stop_id, sections->GetSectionAtIndex(i));
3275 return section_unload_count;
3278 bool Target::SetSectionUnloaded(const lldb::SectionSP &section_sp) {
3279 uint32_t stop_id = 0;
3280 ProcessSP process_sp(GetProcessSP());
3281 if (process_sp)
3282 stop_id = process_sp->GetStopID();
3283 else
3284 stop_id = m_section_load_history.GetLastStopID();
3285 return m_section_load_history.SetSectionUnloaded(stop_id, section_sp);
3288 bool Target::SetSectionUnloaded(const lldb::SectionSP &section_sp,
3289 addr_t load_addr) {
3290 uint32_t stop_id = 0;
3291 ProcessSP process_sp(GetProcessSP());
3292 if (process_sp)
3293 stop_id = process_sp->GetStopID();
3294 else
3295 stop_id = m_section_load_history.GetLastStopID();
3296 return m_section_load_history.SetSectionUnloaded(stop_id, section_sp,
3297 load_addr);
3300 void Target::ClearAllLoadedSections() { m_section_load_history.Clear(); }
3302 lldb_private::SummaryStatisticsSP Target::GetSummaryStatisticsSPForProviderName(
3303 lldb_private::TypeSummaryImpl &summary_provider) {
3304 return m_summary_statistics_cache.GetSummaryStatisticsForProvider(
3305 summary_provider);
3308 SummaryStatisticsCache &Target::GetSummaryStatisticsCache() {
3309 return m_summary_statistics_cache;
3312 void Target::SaveScriptedLaunchInfo(lldb_private::ProcessInfo &process_info) {
3313 if (process_info.IsScriptedProcess()) {
3314 // Only copy scripted process launch options.
3315 ProcessLaunchInfo &default_launch_info = const_cast<ProcessLaunchInfo &>(
3316 GetGlobalProperties().GetProcessLaunchInfo());
3317 default_launch_info.SetProcessPluginName("ScriptedProcess");
3318 default_launch_info.SetScriptedMetadata(process_info.GetScriptedMetadata());
3319 SetProcessLaunchInfo(default_launch_info);
3323 Status Target::Launch(ProcessLaunchInfo &launch_info, Stream *stream) {
3324 m_stats.SetLaunchOrAttachTime();
3325 Status error;
3326 Log *log = GetLog(LLDBLog::Target);
3328 LLDB_LOGF(log, "Target::%s() called for %s", __FUNCTION__,
3329 launch_info.GetExecutableFile().GetPath().c_str());
3331 StateType state = eStateInvalid;
3333 // Scope to temporarily get the process state in case someone has manually
3334 // remotely connected already to a process and we can skip the platform
3335 // launching.
3337 ProcessSP process_sp(GetProcessSP());
3339 if (process_sp) {
3340 state = process_sp->GetState();
3341 LLDB_LOGF(log,
3342 "Target::%s the process exists, and its current state is %s",
3343 __FUNCTION__, StateAsCString(state));
3344 } else {
3345 LLDB_LOGF(log, "Target::%s the process instance doesn't currently exist.",
3346 __FUNCTION__);
3350 launch_info.GetFlags().Set(eLaunchFlagDebug);
3352 SaveScriptedLaunchInfo(launch_info);
3354 // Get the value of synchronous execution here. If you wait till after you
3355 // have started to run, then you could have hit a breakpoint, whose command
3356 // might switch the value, and then you'll pick up that incorrect value.
3357 Debugger &debugger = GetDebugger();
3358 const bool synchronous_execution =
3359 debugger.GetCommandInterpreter().GetSynchronous();
3361 PlatformSP platform_sp(GetPlatform());
3363 FinalizeFileActions(launch_info);
3365 if (state == eStateConnected) {
3366 if (launch_info.GetFlags().Test(eLaunchFlagLaunchInTTY))
3367 return Status::FromErrorString(
3368 "can't launch in tty when launching through a remote connection");
3371 if (!launch_info.GetArchitecture().IsValid())
3372 launch_info.GetArchitecture() = GetArchitecture();
3374 // Hijacking events of the process to be created to be sure that all events
3375 // until the first stop are intercepted (in case if platform doesn't define
3376 // its own hijacking listener or if the process is created by the target
3377 // manually, without the platform).
3378 if (!launch_info.GetHijackListener())
3379 launch_info.SetHijackListener(Listener::MakeListener(
3380 Process::LaunchSynchronousHijackListenerName.data()));
3382 // If we're not already connected to the process, and if we have a platform
3383 // that can launch a process for debugging, go ahead and do that here.
3384 if (state != eStateConnected && platform_sp &&
3385 platform_sp->CanDebugProcess() && !launch_info.IsScriptedProcess()) {
3386 LLDB_LOGF(log, "Target::%s asking the platform to debug the process",
3387 __FUNCTION__);
3389 // If there was a previous process, delete it before we make the new one.
3390 // One subtle point, we delete the process before we release the reference
3391 // to m_process_sp. That way even if we are the last owner, the process
3392 // will get Finalized before it gets destroyed.
3393 DeleteCurrentProcess();
3395 m_process_sp =
3396 GetPlatform()->DebugProcess(launch_info, debugger, *this, error);
3398 } else {
3399 LLDB_LOGF(log,
3400 "Target::%s the platform doesn't know how to debug a "
3401 "process, getting a process plugin to do this for us.",
3402 __FUNCTION__);
3404 if (state == eStateConnected) {
3405 assert(m_process_sp);
3406 } else {
3407 // Use a Process plugin to construct the process.
3408 CreateProcess(launch_info.GetListener(),
3409 launch_info.GetProcessPluginName(), nullptr, false);
3412 // Since we didn't have a platform launch the process, launch it here.
3413 if (m_process_sp) {
3414 m_process_sp->HijackProcessEvents(launch_info.GetHijackListener());
3415 m_process_sp->SetShadowListener(launch_info.GetShadowListener());
3416 error = m_process_sp->Launch(launch_info);
3420 if (!error.Success())
3421 return error;
3423 if (!m_process_sp)
3424 return Status::FromErrorString("failed to launch or debug process");
3426 bool rebroadcast_first_stop =
3427 !synchronous_execution &&
3428 launch_info.GetFlags().Test(eLaunchFlagStopAtEntry);
3430 assert(launch_info.GetHijackListener());
3432 EventSP first_stop_event_sp;
3433 state = m_process_sp->WaitForProcessToStop(std::nullopt, &first_stop_event_sp,
3434 rebroadcast_first_stop,
3435 launch_info.GetHijackListener());
3436 m_process_sp->RestoreProcessEvents();
3438 if (rebroadcast_first_stop) {
3439 assert(first_stop_event_sp);
3440 m_process_sp->BroadcastEvent(first_stop_event_sp);
3441 return error;
3444 switch (state) {
3445 case eStateStopped: {
3446 if (launch_info.GetFlags().Test(eLaunchFlagStopAtEntry))
3447 break;
3448 if (synchronous_execution)
3449 // Now we have handled the stop-from-attach, and we are just
3450 // switching to a synchronous resume. So we should switch to the
3451 // SyncResume hijacker.
3452 m_process_sp->ResumeSynchronous(stream);
3453 else
3454 error = m_process_sp->Resume();
3455 if (!error.Success()) {
3456 error = Status::FromErrorStringWithFormat(
3457 "process resume at entry point failed: %s", error.AsCString());
3459 } break;
3460 case eStateExited: {
3461 bool with_shell = !!launch_info.GetShell();
3462 const int exit_status = m_process_sp->GetExitStatus();
3463 const char *exit_desc = m_process_sp->GetExitDescription();
3464 std::string desc;
3465 if (exit_desc && exit_desc[0])
3466 desc = " (" + std::string(exit_desc) + ')';
3467 if (with_shell)
3468 error = Status::FromErrorStringWithFormat(
3469 "process exited with status %i%s\n"
3470 "'r' and 'run' are aliases that default to launching through a "
3471 "shell.\n"
3472 "Try launching without going through a shell by using "
3473 "'process launch'.",
3474 exit_status, desc.c_str());
3475 else
3476 error = Status::FromErrorStringWithFormat(
3477 "process exited with status %i%s", exit_status, desc.c_str());
3478 } break;
3479 default:
3480 error = Status::FromErrorStringWithFormat(
3481 "initial process state wasn't stopped: %s", StateAsCString(state));
3482 break;
3484 return error;
3487 void Target::SetTrace(const TraceSP &trace_sp) { m_trace_sp = trace_sp; }
3489 TraceSP Target::GetTrace() { return m_trace_sp; }
3491 llvm::Expected<TraceSP> Target::CreateTrace() {
3492 if (!m_process_sp)
3493 return llvm::createStringError(llvm::inconvertibleErrorCode(),
3494 "A process is required for tracing");
3495 if (m_trace_sp)
3496 return llvm::createStringError(llvm::inconvertibleErrorCode(),
3497 "A trace already exists for the target");
3499 llvm::Expected<TraceSupportedResponse> trace_type =
3500 m_process_sp->TraceSupported();
3501 if (!trace_type)
3502 return llvm::createStringError(
3503 llvm::inconvertibleErrorCode(), "Tracing is not supported. %s",
3504 llvm::toString(trace_type.takeError()).c_str());
3505 if (llvm::Expected<TraceSP> trace_sp =
3506 Trace::FindPluginForLiveProcess(trace_type->name, *m_process_sp))
3507 m_trace_sp = *trace_sp;
3508 else
3509 return llvm::createStringError(
3510 llvm::inconvertibleErrorCode(),
3511 "Couldn't create a Trace object for the process. %s",
3512 llvm::toString(trace_sp.takeError()).c_str());
3513 return m_trace_sp;
3516 llvm::Expected<TraceSP> Target::GetTraceOrCreate() {
3517 if (m_trace_sp)
3518 return m_trace_sp;
3519 return CreateTrace();
3522 Status Target::Attach(ProcessAttachInfo &attach_info, Stream *stream) {
3523 m_stats.SetLaunchOrAttachTime();
3524 auto state = eStateInvalid;
3525 auto process_sp = GetProcessSP();
3526 if (process_sp) {
3527 state = process_sp->GetState();
3528 if (process_sp->IsAlive() && state != eStateConnected) {
3529 if (state == eStateAttaching)
3530 return Status::FromErrorString("process attach is in progress");
3531 return Status::FromErrorString("a process is already being debugged");
3535 const ModuleSP old_exec_module_sp = GetExecutableModule();
3537 // If no process info was specified, then use the target executable name as
3538 // the process to attach to by default
3539 if (!attach_info.ProcessInfoSpecified()) {
3540 if (old_exec_module_sp)
3541 attach_info.GetExecutableFile().SetFilename(
3542 old_exec_module_sp->GetPlatformFileSpec().GetFilename());
3544 if (!attach_info.ProcessInfoSpecified()) {
3545 return Status::FromErrorString(
3546 "no process specified, create a target with a file, or "
3547 "specify the --pid or --name");
3551 const auto platform_sp =
3552 GetDebugger().GetPlatformList().GetSelectedPlatform();
3553 ListenerSP hijack_listener_sp;
3554 const bool async = attach_info.GetAsync();
3555 if (!async) {
3556 hijack_listener_sp = Listener::MakeListener(
3557 Process::AttachSynchronousHijackListenerName.data());
3558 attach_info.SetHijackListener(hijack_listener_sp);
3561 Status error;
3562 if (state != eStateConnected && platform_sp != nullptr &&
3563 platform_sp->CanDebugProcess() && !attach_info.IsScriptedProcess()) {
3564 SetPlatform(platform_sp);
3565 process_sp = platform_sp->Attach(attach_info, GetDebugger(), this, error);
3566 } else {
3567 if (state != eStateConnected) {
3568 SaveScriptedLaunchInfo(attach_info);
3569 llvm::StringRef plugin_name = attach_info.GetProcessPluginName();
3570 process_sp =
3571 CreateProcess(attach_info.GetListenerForProcess(GetDebugger()),
3572 plugin_name, nullptr, false);
3573 if (!process_sp) {
3574 error = Status::FromErrorStringWithFormatv(
3575 "failed to create process using plugin '{0}'",
3576 plugin_name.empty() ? "<empty>" : plugin_name);
3577 return error;
3580 if (hijack_listener_sp)
3581 process_sp->HijackProcessEvents(hijack_listener_sp);
3582 error = process_sp->Attach(attach_info);
3585 if (error.Success() && process_sp) {
3586 if (async) {
3587 process_sp->RestoreProcessEvents();
3588 } else {
3589 // We are stopping all the way out to the user, so update selected frames.
3590 state = process_sp->WaitForProcessToStop(
3591 std::nullopt, nullptr, false, attach_info.GetHijackListener(), stream,
3592 true, SelectMostRelevantFrame);
3593 process_sp->RestoreProcessEvents();
3595 if (state != eStateStopped) {
3596 const char *exit_desc = process_sp->GetExitDescription();
3597 if (exit_desc)
3598 error = Status::FromErrorStringWithFormat("%s", exit_desc);
3599 else
3600 error = Status::FromErrorString(
3601 "process did not stop (no such process or permission problem?)");
3602 process_sp->Destroy(false);
3606 return error;
3609 void Target::FinalizeFileActions(ProcessLaunchInfo &info) {
3610 Log *log = GetLog(LLDBLog::Process);
3612 // Finalize the file actions, and if none were given, default to opening up a
3613 // pseudo terminal
3614 PlatformSP platform_sp = GetPlatform();
3615 const bool default_to_use_pty =
3616 m_platform_sp ? m_platform_sp->IsHost() : false;
3617 LLDB_LOG(
3618 log,
3619 "have platform={0}, platform_sp->IsHost()={1}, default_to_use_pty={2}",
3620 bool(platform_sp),
3621 platform_sp ? (platform_sp->IsHost() ? "true" : "false") : "n/a",
3622 default_to_use_pty);
3624 // If nothing for stdin or stdout or stderr was specified, then check the
3625 // process for any default settings that were set with "settings set"
3626 if (info.GetFileActionForFD(STDIN_FILENO) == nullptr ||
3627 info.GetFileActionForFD(STDOUT_FILENO) == nullptr ||
3628 info.GetFileActionForFD(STDERR_FILENO) == nullptr) {
3629 LLDB_LOG(log, "at least one of stdin/stdout/stderr was not set, evaluating "
3630 "default handling");
3632 if (info.GetFlags().Test(eLaunchFlagLaunchInTTY)) {
3633 // Do nothing, if we are launching in a remote terminal no file actions
3634 // should be done at all.
3635 return;
3638 if (info.GetFlags().Test(eLaunchFlagDisableSTDIO)) {
3639 LLDB_LOG(log, "eLaunchFlagDisableSTDIO set, adding suppression action "
3640 "for stdin, stdout and stderr");
3641 info.AppendSuppressFileAction(STDIN_FILENO, true, false);
3642 info.AppendSuppressFileAction(STDOUT_FILENO, false, true);
3643 info.AppendSuppressFileAction(STDERR_FILENO, false, true);
3644 } else {
3645 // Check for any values that might have gotten set with any of: (lldb)
3646 // settings set target.input-path (lldb) settings set target.output-path
3647 // (lldb) settings set target.error-path
3648 FileSpec in_file_spec;
3649 FileSpec out_file_spec;
3650 FileSpec err_file_spec;
3651 // Only override with the target settings if we don't already have an
3652 // action for in, out or error
3653 if (info.GetFileActionForFD(STDIN_FILENO) == nullptr)
3654 in_file_spec = GetStandardInputPath();
3655 if (info.GetFileActionForFD(STDOUT_FILENO) == nullptr)
3656 out_file_spec = GetStandardOutputPath();
3657 if (info.GetFileActionForFD(STDERR_FILENO) == nullptr)
3658 err_file_spec = GetStandardErrorPath();
3660 LLDB_LOG(log, "target stdin='{0}', target stdout='{1}', stderr='{2}'",
3661 in_file_spec, out_file_spec, err_file_spec);
3663 if (in_file_spec) {
3664 info.AppendOpenFileAction(STDIN_FILENO, in_file_spec, true, false);
3665 LLDB_LOG(log, "appended stdin open file action for {0}", in_file_spec);
3668 if (out_file_spec) {
3669 info.AppendOpenFileAction(STDOUT_FILENO, out_file_spec, false, true);
3670 LLDB_LOG(log, "appended stdout open file action for {0}",
3671 out_file_spec);
3674 if (err_file_spec) {
3675 info.AppendOpenFileAction(STDERR_FILENO, err_file_spec, false, true);
3676 LLDB_LOG(log, "appended stderr open file action for {0}",
3677 err_file_spec);
3680 if (default_to_use_pty) {
3681 llvm::Error Err = info.SetUpPtyRedirection();
3682 LLDB_LOG_ERROR(log, std::move(Err), "SetUpPtyRedirection failed: {0}");
3688 void Target::AddDummySignal(llvm::StringRef name, LazyBool pass, LazyBool notify,
3689 LazyBool stop) {
3690 if (name.empty())
3691 return;
3692 // Don't add a signal if all the actions are trivial:
3693 if (pass == eLazyBoolCalculate && notify == eLazyBoolCalculate
3694 && stop == eLazyBoolCalculate)
3695 return;
3697 auto& elem = m_dummy_signals[name];
3698 elem.pass = pass;
3699 elem.notify = notify;
3700 elem.stop = stop;
3703 bool Target::UpdateSignalFromDummy(UnixSignalsSP signals_sp,
3704 const DummySignalElement &elem) {
3705 if (!signals_sp)
3706 return false;
3708 int32_t signo
3709 = signals_sp->GetSignalNumberFromName(elem.first().str().c_str());
3710 if (signo == LLDB_INVALID_SIGNAL_NUMBER)
3711 return false;
3713 if (elem.second.pass == eLazyBoolYes)
3714 signals_sp->SetShouldSuppress(signo, false);
3715 else if (elem.second.pass == eLazyBoolNo)
3716 signals_sp->SetShouldSuppress(signo, true);
3718 if (elem.second.notify == eLazyBoolYes)
3719 signals_sp->SetShouldNotify(signo, true);
3720 else if (elem.second.notify == eLazyBoolNo)
3721 signals_sp->SetShouldNotify(signo, false);
3723 if (elem.second.stop == eLazyBoolYes)
3724 signals_sp->SetShouldStop(signo, true);
3725 else if (elem.second.stop == eLazyBoolNo)
3726 signals_sp->SetShouldStop(signo, false);
3727 return true;
3730 bool Target::ResetSignalFromDummy(UnixSignalsSP signals_sp,
3731 const DummySignalElement &elem) {
3732 if (!signals_sp)
3733 return false;
3734 int32_t signo
3735 = signals_sp->GetSignalNumberFromName(elem.first().str().c_str());
3736 if (signo == LLDB_INVALID_SIGNAL_NUMBER)
3737 return false;
3738 bool do_pass = elem.second.pass != eLazyBoolCalculate;
3739 bool do_stop = elem.second.stop != eLazyBoolCalculate;
3740 bool do_notify = elem.second.notify != eLazyBoolCalculate;
3741 signals_sp->ResetSignal(signo, do_stop, do_notify, do_pass);
3742 return true;
3745 void Target::UpdateSignalsFromDummy(UnixSignalsSP signals_sp,
3746 StreamSP warning_stream_sp) {
3747 if (!signals_sp)
3748 return;
3750 for (const auto &elem : m_dummy_signals) {
3751 if (!UpdateSignalFromDummy(signals_sp, elem))
3752 warning_stream_sp->Printf("Target signal '%s' not found in process\n",
3753 elem.first().str().c_str());
3757 void Target::ClearDummySignals(Args &signal_names) {
3758 ProcessSP process_sp = GetProcessSP();
3759 // The simplest case, delete them all with no process to update.
3760 if (signal_names.GetArgumentCount() == 0 && !process_sp) {
3761 m_dummy_signals.clear();
3762 return;
3764 UnixSignalsSP signals_sp;
3765 if (process_sp)
3766 signals_sp = process_sp->GetUnixSignals();
3768 for (const Args::ArgEntry &entry : signal_names) {
3769 const char *signal_name = entry.c_str();
3770 auto elem = m_dummy_signals.find(signal_name);
3771 // If we didn't find it go on.
3772 // FIXME: Should I pipe error handling through here?
3773 if (elem == m_dummy_signals.end()) {
3774 continue;
3776 if (signals_sp)
3777 ResetSignalFromDummy(signals_sp, *elem);
3778 m_dummy_signals.erase(elem);
3782 void Target::PrintDummySignals(Stream &strm, Args &signal_args) {
3783 strm.Printf("NAME PASS STOP NOTIFY\n");
3784 strm.Printf("=========== ======= ======= =======\n");
3786 auto str_for_lazy = [] (LazyBool lazy) -> const char * {
3787 switch (lazy) {
3788 case eLazyBoolCalculate: return "not set";
3789 case eLazyBoolYes: return "true ";
3790 case eLazyBoolNo: return "false ";
3792 llvm_unreachable("Fully covered switch above!");
3794 size_t num_args = signal_args.GetArgumentCount();
3795 for (const auto &elem : m_dummy_signals) {
3796 bool print_it = false;
3797 for (size_t idx = 0; idx < num_args; idx++) {
3798 if (elem.first() == signal_args.GetArgumentAtIndex(idx)) {
3799 print_it = true;
3800 break;
3803 if (print_it) {
3804 strm.Printf("%-11s ", elem.first().str().c_str());
3805 strm.Printf("%s %s %s\n", str_for_lazy(elem.second.pass),
3806 str_for_lazy(elem.second.stop),
3807 str_for_lazy(elem.second.notify));
3812 // Target::StopHook
3813 Target::StopHook::StopHook(lldb::TargetSP target_sp, lldb::user_id_t uid)
3814 : UserID(uid), m_target_sp(target_sp), m_specifier_sp(),
3815 m_thread_spec_up() {}
3817 Target::StopHook::StopHook(const StopHook &rhs)
3818 : UserID(rhs.GetID()), m_target_sp(rhs.m_target_sp),
3819 m_specifier_sp(rhs.m_specifier_sp), m_thread_spec_up(),
3820 m_active(rhs.m_active), m_auto_continue(rhs.m_auto_continue) {
3821 if (rhs.m_thread_spec_up)
3822 m_thread_spec_up = std::make_unique<ThreadSpec>(*rhs.m_thread_spec_up);
3825 void Target::StopHook::SetSpecifier(SymbolContextSpecifier *specifier) {
3826 m_specifier_sp.reset(specifier);
3829 void Target::StopHook::SetThreadSpecifier(ThreadSpec *specifier) {
3830 m_thread_spec_up.reset(specifier);
3833 bool Target::StopHook::ExecutionContextPasses(const ExecutionContext &exc_ctx) {
3834 SymbolContextSpecifier *specifier = GetSpecifier();
3835 if (!specifier)
3836 return true;
3838 bool will_run = true;
3839 if (exc_ctx.GetFramePtr())
3840 will_run = GetSpecifier()->SymbolContextMatches(
3841 exc_ctx.GetFramePtr()->GetSymbolContext(eSymbolContextEverything));
3842 if (will_run && GetThreadSpecifier() != nullptr)
3843 will_run =
3844 GetThreadSpecifier()->ThreadPassesBasicTests(exc_ctx.GetThreadRef());
3846 return will_run;
3849 void Target::StopHook::GetDescription(Stream &s,
3850 lldb::DescriptionLevel level) const {
3852 // For brief descriptions, only print the subclass description:
3853 if (level == eDescriptionLevelBrief) {
3854 GetSubclassDescription(s, level);
3855 return;
3858 unsigned indent_level = s.GetIndentLevel();
3860 s.SetIndentLevel(indent_level + 2);
3862 s.Printf("Hook: %" PRIu64 "\n", GetID());
3863 if (m_active)
3864 s.Indent("State: enabled\n");
3865 else
3866 s.Indent("State: disabled\n");
3868 if (m_auto_continue)
3869 s.Indent("AutoContinue on\n");
3871 if (m_specifier_sp) {
3872 s.Indent();
3873 s.PutCString("Specifier:\n");
3874 s.SetIndentLevel(indent_level + 4);
3875 m_specifier_sp->GetDescription(&s, level);
3876 s.SetIndentLevel(indent_level + 2);
3879 if (m_thread_spec_up) {
3880 StreamString tmp;
3881 s.Indent("Thread:\n");
3882 m_thread_spec_up->GetDescription(&tmp, level);
3883 s.SetIndentLevel(indent_level + 4);
3884 s.Indent(tmp.GetString());
3885 s.PutCString("\n");
3886 s.SetIndentLevel(indent_level + 2);
3888 GetSubclassDescription(s, level);
3891 void Target::StopHookCommandLine::GetSubclassDescription(
3892 Stream &s, lldb::DescriptionLevel level) const {
3893 // The brief description just prints the first command.
3894 if (level == eDescriptionLevelBrief) {
3895 if (m_commands.GetSize() == 1)
3896 s.PutCString(m_commands.GetStringAtIndex(0));
3897 return;
3899 s.Indent("Commands: \n");
3900 s.SetIndentLevel(s.GetIndentLevel() + 4);
3901 uint32_t num_commands = m_commands.GetSize();
3902 for (uint32_t i = 0; i < num_commands; i++) {
3903 s.Indent(m_commands.GetStringAtIndex(i));
3904 s.PutCString("\n");
3906 s.SetIndentLevel(s.GetIndentLevel() - 4);
3909 // Target::StopHookCommandLine
3910 void Target::StopHookCommandLine::SetActionFromString(const std::string &string) {
3911 GetCommands().SplitIntoLines(string);
3914 void Target::StopHookCommandLine::SetActionFromStrings(
3915 const std::vector<std::string> &strings) {
3916 for (auto string : strings)
3917 GetCommands().AppendString(string.c_str());
3920 Target::StopHook::StopHookResult
3921 Target::StopHookCommandLine::HandleStop(ExecutionContext &exc_ctx,
3922 StreamSP output_sp) {
3923 assert(exc_ctx.GetTargetPtr() && "Can't call PerformAction on a context "
3924 "with no target");
3926 if (!m_commands.GetSize())
3927 return StopHookResult::KeepStopped;
3929 CommandReturnObject result(false);
3930 result.SetImmediateOutputStream(output_sp);
3931 result.SetInteractive(false);
3932 Debugger &debugger = exc_ctx.GetTargetPtr()->GetDebugger();
3933 CommandInterpreterRunOptions options;
3934 options.SetStopOnContinue(true);
3935 options.SetStopOnError(true);
3936 options.SetEchoCommands(false);
3937 options.SetPrintResults(true);
3938 options.SetPrintErrors(true);
3939 options.SetAddToHistory(false);
3941 // Force Async:
3942 bool old_async = debugger.GetAsyncExecution();
3943 debugger.SetAsyncExecution(true);
3944 debugger.GetCommandInterpreter().HandleCommands(GetCommands(), exc_ctx,
3945 options, result);
3946 debugger.SetAsyncExecution(old_async);
3947 lldb::ReturnStatus status = result.GetStatus();
3948 if (status == eReturnStatusSuccessContinuingNoResult ||
3949 status == eReturnStatusSuccessContinuingResult)
3950 return StopHookResult::AlreadyContinued;
3951 return StopHookResult::KeepStopped;
3954 // Target::StopHookScripted
3955 Status Target::StopHookScripted::SetScriptCallback(
3956 std::string class_name, StructuredData::ObjectSP extra_args_sp) {
3957 Status error;
3959 ScriptInterpreter *script_interp =
3960 GetTarget()->GetDebugger().GetScriptInterpreter();
3961 if (!script_interp) {
3962 error = Status::FromErrorString("No script interpreter installed.");
3963 return error;
3966 m_interface_sp = script_interp->CreateScriptedStopHookInterface();
3967 if (!m_interface_sp) {
3968 error = Status::FromErrorStringWithFormat(
3969 "ScriptedStopHook::%s () - ERROR: %s", __FUNCTION__,
3970 "Script interpreter couldn't create Scripted Stop Hook Interface");
3971 return error;
3974 m_class_name = class_name;
3975 m_extra_args.SetObjectSP(extra_args_sp);
3977 auto obj_or_err = m_interface_sp->CreatePluginObject(
3978 m_class_name, GetTarget(), m_extra_args);
3979 if (!obj_or_err) {
3980 return Status::FromError(obj_or_err.takeError());
3983 StructuredData::ObjectSP object_sp = *obj_or_err;
3984 if (!object_sp || !object_sp->IsValid()) {
3985 error = Status::FromErrorStringWithFormat(
3986 "ScriptedStopHook::%s () - ERROR: %s", __FUNCTION__,
3987 "Failed to create valid script object");
3988 return error;
3991 return {};
3994 Target::StopHook::StopHookResult
3995 Target::StopHookScripted::HandleStop(ExecutionContext &exc_ctx,
3996 StreamSP output_sp) {
3997 assert(exc_ctx.GetTargetPtr() && "Can't call HandleStop on a context "
3998 "with no target");
4000 if (!m_interface_sp)
4001 return StopHookResult::KeepStopped;
4003 lldb::StreamSP stream = std::make_shared<lldb_private::StreamString>();
4004 auto should_stop_or_err = m_interface_sp->HandleStop(exc_ctx, stream);
4005 output_sp->PutCString(
4006 reinterpret_cast<StreamString *>(stream.get())->GetData());
4007 if (!should_stop_or_err)
4008 return StopHookResult::KeepStopped;
4010 return *should_stop_or_err ? StopHookResult::KeepStopped
4011 : StopHookResult::RequestContinue;
4014 void Target::StopHookScripted::GetSubclassDescription(
4015 Stream &s, lldb::DescriptionLevel level) const {
4016 if (level == eDescriptionLevelBrief) {
4017 s.PutCString(m_class_name);
4018 return;
4020 s.Indent("Class:");
4021 s.Printf("%s\n", m_class_name.c_str());
4023 // Now print the extra args:
4024 // FIXME: We should use StructuredData.GetDescription on the m_extra_args
4025 // but that seems to rely on some printing plugin that doesn't exist.
4026 if (!m_extra_args.IsValid())
4027 return;
4028 StructuredData::ObjectSP object_sp = m_extra_args.GetObjectSP();
4029 if (!object_sp || !object_sp->IsValid())
4030 return;
4032 StructuredData::Dictionary *as_dict = object_sp->GetAsDictionary();
4033 if (!as_dict || !as_dict->IsValid())
4034 return;
4036 uint32_t num_keys = as_dict->GetSize();
4037 if (num_keys == 0)
4038 return;
4040 s.Indent("Args:\n");
4041 s.SetIndentLevel(s.GetIndentLevel() + 4);
4043 auto print_one_element = [&s](llvm::StringRef key,
4044 StructuredData::Object *object) {
4045 s.Indent();
4046 s.Format("{0} : {1}\n", key, object->GetStringValue());
4047 return true;
4050 as_dict->ForEach(print_one_element);
4052 s.SetIndentLevel(s.GetIndentLevel() - 4);
4055 static constexpr OptionEnumValueElement g_dynamic_value_types[] = {
4057 eNoDynamicValues,
4058 "no-dynamic-values",
4059 "Don't calculate the dynamic type of values",
4062 eDynamicCanRunTarget,
4063 "run-target",
4064 "Calculate the dynamic type of values "
4065 "even if you have to run the target.",
4068 eDynamicDontRunTarget,
4069 "no-run-target",
4070 "Calculate the dynamic type of values, but don't run the target.",
4074 OptionEnumValues lldb_private::GetDynamicValueTypes() {
4075 return OptionEnumValues(g_dynamic_value_types);
4078 static constexpr OptionEnumValueElement g_inline_breakpoint_enums[] = {
4080 eInlineBreakpointsNever,
4081 "never",
4082 "Never look for inline breakpoint locations (fastest). This setting "
4083 "should only be used if you know that no inlining occurs in your"
4084 "programs.",
4087 eInlineBreakpointsHeaders,
4088 "headers",
4089 "Only check for inline breakpoint locations when setting breakpoints "
4090 "in header files, but not when setting breakpoint in implementation "
4091 "source files (default).",
4094 eInlineBreakpointsAlways,
4095 "always",
4096 "Always look for inline breakpoint locations when setting file and "
4097 "line breakpoints (slower but most accurate).",
4101 enum x86DisassemblyFlavor {
4102 eX86DisFlavorDefault,
4103 eX86DisFlavorIntel,
4104 eX86DisFlavorATT
4107 static constexpr OptionEnumValueElement g_x86_dis_flavor_value_types[] = {
4109 eX86DisFlavorDefault,
4110 "default",
4111 "Disassembler default (currently att).",
4114 eX86DisFlavorIntel,
4115 "intel",
4116 "Intel disassembler flavor.",
4119 eX86DisFlavorATT,
4120 "att",
4121 "AT&T disassembler flavor.",
4125 static constexpr OptionEnumValueElement g_import_std_module_value_types[] = {
4127 eImportStdModuleFalse,
4128 "false",
4129 "Never import the 'std' C++ module in the expression parser.",
4132 eImportStdModuleFallback,
4133 "fallback",
4134 "Retry evaluating expressions with an imported 'std' C++ module if they"
4135 " failed to parse without the module. This allows evaluating more "
4136 "complex expressions involving C++ standard library types."
4139 eImportStdModuleTrue,
4140 "true",
4141 "Always import the 'std' C++ module. This allows evaluating more "
4142 "complex expressions involving C++ standard library types. This feature"
4143 " is experimental."
4147 static constexpr OptionEnumValueElement
4148 g_dynamic_class_info_helper_value_types[] = {
4150 eDynamicClassInfoHelperAuto,
4151 "auto",
4152 "Automatically determine the most appropriate method for the "
4153 "target OS.",
4155 {eDynamicClassInfoHelperRealizedClassesStruct, "RealizedClassesStruct",
4156 "Prefer using the realized classes struct."},
4157 {eDynamicClassInfoHelperCopyRealizedClassList, "CopyRealizedClassList",
4158 "Prefer using the CopyRealizedClassList API."},
4159 {eDynamicClassInfoHelperGetRealizedClassList, "GetRealizedClassList",
4160 "Prefer using the GetRealizedClassList API."},
4163 static constexpr OptionEnumValueElement g_hex_immediate_style_values[] = {
4165 Disassembler::eHexStyleC,
4166 "c",
4167 "C-style (0xffff).",
4170 Disassembler::eHexStyleAsm,
4171 "asm",
4172 "Asm-style (0ffffh).",
4176 static constexpr OptionEnumValueElement g_load_script_from_sym_file_values[] = {
4178 eLoadScriptFromSymFileTrue,
4179 "true",
4180 "Load debug scripts inside symbol files",
4183 eLoadScriptFromSymFileFalse,
4184 "false",
4185 "Do not load debug scripts inside symbol files.",
4188 eLoadScriptFromSymFileWarn,
4189 "warn",
4190 "Warn about debug scripts inside symbol files but do not load them.",
4194 static constexpr OptionEnumValueElement g_load_cwd_lldbinit_values[] = {
4196 eLoadCWDlldbinitTrue,
4197 "true",
4198 "Load .lldbinit files from current directory",
4201 eLoadCWDlldbinitFalse,
4202 "false",
4203 "Do not load .lldbinit files from current directory",
4206 eLoadCWDlldbinitWarn,
4207 "warn",
4208 "Warn about loading .lldbinit files from current directory",
4212 static constexpr OptionEnumValueElement g_memory_module_load_level_values[] = {
4214 eMemoryModuleLoadLevelMinimal,
4215 "minimal",
4216 "Load minimal information when loading modules from memory. Currently "
4217 "this setting loads sections only.",
4220 eMemoryModuleLoadLevelPartial,
4221 "partial",
4222 "Load partial information when loading modules from memory. Currently "
4223 "this setting loads sections and function bounds.",
4226 eMemoryModuleLoadLevelComplete,
4227 "complete",
4228 "Load complete information when loading modules from memory. Currently "
4229 "this setting loads sections and all symbols.",
4233 #define LLDB_PROPERTIES_target
4234 #include "TargetProperties.inc"
4236 enum {
4237 #define LLDB_PROPERTIES_target
4238 #include "TargetPropertiesEnum.inc"
4239 ePropertyExperimental,
4242 class TargetOptionValueProperties
4243 : public Cloneable<TargetOptionValueProperties, OptionValueProperties> {
4244 public:
4245 TargetOptionValueProperties(llvm::StringRef name) : Cloneable(name) {}
4247 const Property *
4248 GetPropertyAtIndex(size_t idx,
4249 const ExecutionContext *exe_ctx = nullptr) const override {
4250 // When getting the value for a key from the target options, we will always
4251 // try and grab the setting from the current target if there is one. Else
4252 // we just use the one from this instance.
4253 if (exe_ctx) {
4254 Target *target = exe_ctx->GetTargetPtr();
4255 if (target) {
4256 TargetOptionValueProperties *target_properties =
4257 static_cast<TargetOptionValueProperties *>(
4258 target->GetValueProperties().get());
4259 if (this != target_properties)
4260 return target_properties->ProtectedGetPropertyAtIndex(idx);
4263 return ProtectedGetPropertyAtIndex(idx);
4267 // TargetProperties
4268 #define LLDB_PROPERTIES_target_experimental
4269 #include "TargetProperties.inc"
4271 enum {
4272 #define LLDB_PROPERTIES_target_experimental
4273 #include "TargetPropertiesEnum.inc"
4276 class TargetExperimentalOptionValueProperties
4277 : public Cloneable<TargetExperimentalOptionValueProperties,
4278 OptionValueProperties> {
4279 public:
4280 TargetExperimentalOptionValueProperties()
4281 : Cloneable(Properties::GetExperimentalSettingsName()) {}
4284 TargetExperimentalProperties::TargetExperimentalProperties()
4285 : Properties(OptionValuePropertiesSP(
4286 new TargetExperimentalOptionValueProperties())) {
4287 m_collection_sp->Initialize(g_target_experimental_properties);
4290 // TargetProperties
4291 TargetProperties::TargetProperties(Target *target)
4292 : Properties(), m_launch_info(), m_target(target) {
4293 if (target) {
4294 m_collection_sp =
4295 OptionValueProperties::CreateLocalCopy(Target::GetGlobalProperties());
4297 // Set callbacks to update launch_info whenever "settins set" updated any
4298 // of these properties
4299 m_collection_sp->SetValueChangedCallback(
4300 ePropertyArg0, [this] { Arg0ValueChangedCallback(); });
4301 m_collection_sp->SetValueChangedCallback(
4302 ePropertyRunArgs, [this] { RunArgsValueChangedCallback(); });
4303 m_collection_sp->SetValueChangedCallback(
4304 ePropertyEnvVars, [this] { EnvVarsValueChangedCallback(); });
4305 m_collection_sp->SetValueChangedCallback(
4306 ePropertyUnsetEnvVars, [this] { EnvVarsValueChangedCallback(); });
4307 m_collection_sp->SetValueChangedCallback(
4308 ePropertyInheritEnv, [this] { EnvVarsValueChangedCallback(); });
4309 m_collection_sp->SetValueChangedCallback(
4310 ePropertyInputPath, [this] { InputPathValueChangedCallback(); });
4311 m_collection_sp->SetValueChangedCallback(
4312 ePropertyOutputPath, [this] { OutputPathValueChangedCallback(); });
4313 m_collection_sp->SetValueChangedCallback(
4314 ePropertyErrorPath, [this] { ErrorPathValueChangedCallback(); });
4315 m_collection_sp->SetValueChangedCallback(ePropertyDetachOnError, [this] {
4316 DetachOnErrorValueChangedCallback();
4318 m_collection_sp->SetValueChangedCallback(
4319 ePropertyDisableASLR, [this] { DisableASLRValueChangedCallback(); });
4320 m_collection_sp->SetValueChangedCallback(
4321 ePropertyInheritTCC, [this] { InheritTCCValueChangedCallback(); });
4322 m_collection_sp->SetValueChangedCallback(
4323 ePropertyDisableSTDIO, [this] { DisableSTDIOValueChangedCallback(); });
4325 m_collection_sp->SetValueChangedCallback(
4326 ePropertySaveObjectsDir, [this] { CheckJITObjectsDir(); });
4327 m_experimental_properties_up =
4328 std::make_unique<TargetExperimentalProperties>();
4329 m_collection_sp->AppendProperty(
4330 Properties::GetExperimentalSettingsName(),
4331 "Experimental settings - setting these won't produce "
4332 "errors if the setting is not present.",
4333 true, m_experimental_properties_up->GetValueProperties());
4334 } else {
4335 m_collection_sp = std::make_shared<TargetOptionValueProperties>("target");
4336 m_collection_sp->Initialize(g_target_properties);
4337 m_experimental_properties_up =
4338 std::make_unique<TargetExperimentalProperties>();
4339 m_collection_sp->AppendProperty(
4340 Properties::GetExperimentalSettingsName(),
4341 "Experimental settings - setting these won't produce "
4342 "errors if the setting is not present.",
4343 true, m_experimental_properties_up->GetValueProperties());
4344 m_collection_sp->AppendProperty(
4345 "process", "Settings specific to processes.", true,
4346 Process::GetGlobalProperties().GetValueProperties());
4347 m_collection_sp->SetValueChangedCallback(
4348 ePropertySaveObjectsDir, [this] { CheckJITObjectsDir(); });
4352 TargetProperties::~TargetProperties() = default;
4354 void TargetProperties::UpdateLaunchInfoFromProperties() {
4355 Arg0ValueChangedCallback();
4356 RunArgsValueChangedCallback();
4357 EnvVarsValueChangedCallback();
4358 InputPathValueChangedCallback();
4359 OutputPathValueChangedCallback();
4360 ErrorPathValueChangedCallback();
4361 DetachOnErrorValueChangedCallback();
4362 DisableASLRValueChangedCallback();
4363 InheritTCCValueChangedCallback();
4364 DisableSTDIOValueChangedCallback();
4367 std::optional<bool> TargetProperties::GetExperimentalPropertyValue(
4368 size_t prop_idx, ExecutionContext *exe_ctx) const {
4369 const Property *exp_property =
4370 m_collection_sp->GetPropertyAtIndex(ePropertyExperimental, exe_ctx);
4371 OptionValueProperties *exp_values =
4372 exp_property->GetValue()->GetAsProperties();
4373 if (exp_values)
4374 return exp_values->GetPropertyAtIndexAs<bool>(prop_idx, exe_ctx);
4375 return std::nullopt;
4378 bool TargetProperties::GetInjectLocalVariables(
4379 ExecutionContext *exe_ctx) const {
4380 return GetExperimentalPropertyValue(ePropertyInjectLocalVars, exe_ctx)
4381 .value_or(true);
4384 bool TargetProperties::GetUseDIL(ExecutionContext *exe_ctx) const {
4385 const Property *exp_property =
4386 m_collection_sp->GetPropertyAtIndex(ePropertyExperimental, exe_ctx);
4387 OptionValueProperties *exp_values =
4388 exp_property->GetValue()->GetAsProperties();
4389 if (exp_values)
4390 return exp_values->GetPropertyAtIndexAs<bool>(ePropertyUseDIL, exe_ctx)
4391 .value_or(false);
4392 else
4393 return true;
4396 void TargetProperties::SetUseDIL(ExecutionContext *exe_ctx, bool b) {
4397 const Property *exp_property =
4398 m_collection_sp->GetPropertyAtIndex(ePropertyExperimental, exe_ctx);
4399 OptionValueProperties *exp_values =
4400 exp_property->GetValue()->GetAsProperties();
4401 if (exp_values)
4402 exp_values->SetPropertyAtIndex(ePropertyUseDIL, true, exe_ctx);
4405 ArchSpec TargetProperties::GetDefaultArchitecture() const {
4406 const uint32_t idx = ePropertyDefaultArch;
4407 return GetPropertyAtIndexAs<ArchSpec>(idx, {});
4410 void TargetProperties::SetDefaultArchitecture(const ArchSpec &arch) {
4411 const uint32_t idx = ePropertyDefaultArch;
4412 SetPropertyAtIndex(idx, arch);
4415 bool TargetProperties::GetMoveToNearestCode() const {
4416 const uint32_t idx = ePropertyMoveToNearestCode;
4417 return GetPropertyAtIndexAs<bool>(
4418 idx, g_target_properties[idx].default_uint_value != 0);
4421 lldb::DynamicValueType TargetProperties::GetPreferDynamicValue() const {
4422 const uint32_t idx = ePropertyPreferDynamic;
4423 return GetPropertyAtIndexAs<lldb::DynamicValueType>(
4424 idx, static_cast<lldb::DynamicValueType>(
4425 g_target_properties[idx].default_uint_value));
4428 bool TargetProperties::SetPreferDynamicValue(lldb::DynamicValueType d) {
4429 const uint32_t idx = ePropertyPreferDynamic;
4430 return SetPropertyAtIndex(idx, d);
4433 bool TargetProperties::GetPreloadSymbols() const {
4434 if (INTERRUPT_REQUESTED(m_target->GetDebugger(),
4435 "Interrupted checking preload symbols")) {
4436 return false;
4438 const uint32_t idx = ePropertyPreloadSymbols;
4439 return GetPropertyAtIndexAs<bool>(
4440 idx, g_target_properties[idx].default_uint_value != 0);
4443 void TargetProperties::SetPreloadSymbols(bool b) {
4444 const uint32_t idx = ePropertyPreloadSymbols;
4445 SetPropertyAtIndex(idx, b);
4448 bool TargetProperties::GetDisableASLR() const {
4449 const uint32_t idx = ePropertyDisableASLR;
4450 return GetPropertyAtIndexAs<bool>(
4451 idx, g_target_properties[idx].default_uint_value != 0);
4454 void TargetProperties::SetDisableASLR(bool b) {
4455 const uint32_t idx = ePropertyDisableASLR;
4456 SetPropertyAtIndex(idx, b);
4459 bool TargetProperties::GetInheritTCC() const {
4460 const uint32_t idx = ePropertyInheritTCC;
4461 return GetPropertyAtIndexAs<bool>(
4462 idx, g_target_properties[idx].default_uint_value != 0);
4465 void TargetProperties::SetInheritTCC(bool b) {
4466 const uint32_t idx = ePropertyInheritTCC;
4467 SetPropertyAtIndex(idx, b);
4470 bool TargetProperties::GetDetachOnError() const {
4471 const uint32_t idx = ePropertyDetachOnError;
4472 return GetPropertyAtIndexAs<bool>(
4473 idx, g_target_properties[idx].default_uint_value != 0);
4476 void TargetProperties::SetDetachOnError(bool b) {
4477 const uint32_t idx = ePropertyDetachOnError;
4478 SetPropertyAtIndex(idx, b);
4481 bool TargetProperties::GetDisableSTDIO() const {
4482 const uint32_t idx = ePropertyDisableSTDIO;
4483 return GetPropertyAtIndexAs<bool>(
4484 idx, g_target_properties[idx].default_uint_value != 0);
4487 void TargetProperties::SetDisableSTDIO(bool b) {
4488 const uint32_t idx = ePropertyDisableSTDIO;
4489 SetPropertyAtIndex(idx, b);
4491 llvm::StringRef TargetProperties::GetLaunchWorkingDirectory() const {
4492 const uint32_t idx = ePropertyLaunchWorkingDir;
4493 return GetPropertyAtIndexAs<llvm::StringRef>(
4494 idx, g_target_properties[idx].default_cstr_value);
4497 const char *TargetProperties::GetDisassemblyFlavor() const {
4498 const uint32_t idx = ePropertyDisassemblyFlavor;
4499 const char *return_value;
4501 x86DisassemblyFlavor flavor_value =
4502 GetPropertyAtIndexAs<x86DisassemblyFlavor>(
4503 idx, static_cast<x86DisassemblyFlavor>(
4504 g_target_properties[idx].default_uint_value));
4506 return_value = g_x86_dis_flavor_value_types[flavor_value].string_value;
4507 return return_value;
4510 const char *TargetProperties::GetDisassemblyCPU() const {
4511 const uint32_t idx = ePropertyDisassemblyCPU;
4512 llvm::StringRef str = GetPropertyAtIndexAs<llvm::StringRef>(
4513 idx, g_target_properties[idx].default_cstr_value);
4514 return str.empty() ? nullptr : str.data();
4517 const char *TargetProperties::GetDisassemblyFeatures() const {
4518 const uint32_t idx = ePropertyDisassemblyFeatures;
4519 llvm::StringRef str = GetPropertyAtIndexAs<llvm::StringRef>(
4520 idx, g_target_properties[idx].default_cstr_value);
4521 return str.empty() ? nullptr : str.data();
4524 InlineStrategy TargetProperties::GetInlineStrategy() const {
4525 const uint32_t idx = ePropertyInlineStrategy;
4526 return GetPropertyAtIndexAs<InlineStrategy>(
4527 idx,
4528 static_cast<InlineStrategy>(g_target_properties[idx].default_uint_value));
4531 // Returning RealpathPrefixes, but the setting's type is FileSpecList. We do
4532 // this because we want the FileSpecList to normalize the file paths for us.
4533 RealpathPrefixes TargetProperties::GetSourceRealpathPrefixes() const {
4534 const uint32_t idx = ePropertySourceRealpathPrefixes;
4535 return RealpathPrefixes(GetPropertyAtIndexAs<FileSpecList>(idx, {}));
4538 llvm::StringRef TargetProperties::GetArg0() const {
4539 const uint32_t idx = ePropertyArg0;
4540 return GetPropertyAtIndexAs<llvm::StringRef>(
4541 idx, g_target_properties[idx].default_cstr_value);
4544 void TargetProperties::SetArg0(llvm::StringRef arg) {
4545 const uint32_t idx = ePropertyArg0;
4546 SetPropertyAtIndex(idx, arg);
4547 m_launch_info.SetArg0(arg);
4550 bool TargetProperties::GetRunArguments(Args &args) const {
4551 const uint32_t idx = ePropertyRunArgs;
4552 return m_collection_sp->GetPropertyAtIndexAsArgs(idx, args);
4555 void TargetProperties::SetRunArguments(const Args &args) {
4556 const uint32_t idx = ePropertyRunArgs;
4557 m_collection_sp->SetPropertyAtIndexFromArgs(idx, args);
4558 m_launch_info.GetArguments() = args;
4561 Environment TargetProperties::ComputeEnvironment() const {
4562 Environment env;
4564 if (m_target &&
4565 GetPropertyAtIndexAs<bool>(
4566 ePropertyInheritEnv,
4567 g_target_properties[ePropertyInheritEnv].default_uint_value != 0)) {
4568 if (auto platform_sp = m_target->GetPlatform()) {
4569 Environment platform_env = platform_sp->GetEnvironment();
4570 for (const auto &KV : platform_env)
4571 env[KV.first()] = KV.second;
4575 Args property_unset_env;
4576 m_collection_sp->GetPropertyAtIndexAsArgs(ePropertyUnsetEnvVars,
4577 property_unset_env);
4578 for (const auto &var : property_unset_env)
4579 env.erase(var.ref());
4581 Args property_env;
4582 m_collection_sp->GetPropertyAtIndexAsArgs(ePropertyEnvVars, property_env);
4583 for (const auto &KV : Environment(property_env))
4584 env[KV.first()] = KV.second;
4586 return env;
4589 Environment TargetProperties::GetEnvironment() const {
4590 return ComputeEnvironment();
4593 Environment TargetProperties::GetInheritedEnvironment() const {
4594 Environment environment;
4596 if (m_target == nullptr)
4597 return environment;
4599 if (!GetPropertyAtIndexAs<bool>(
4600 ePropertyInheritEnv,
4601 g_target_properties[ePropertyInheritEnv].default_uint_value != 0))
4602 return environment;
4604 PlatformSP platform_sp = m_target->GetPlatform();
4605 if (platform_sp == nullptr)
4606 return environment;
4608 Environment platform_environment = platform_sp->GetEnvironment();
4609 for (const auto &KV : platform_environment)
4610 environment[KV.first()] = KV.second;
4612 Args property_unset_environment;
4613 m_collection_sp->GetPropertyAtIndexAsArgs(ePropertyUnsetEnvVars,
4614 property_unset_environment);
4615 for (const auto &var : property_unset_environment)
4616 environment.erase(var.ref());
4618 return environment;
4621 Environment TargetProperties::GetTargetEnvironment() const {
4622 Args property_environment;
4623 m_collection_sp->GetPropertyAtIndexAsArgs(ePropertyEnvVars,
4624 property_environment);
4625 Environment environment;
4626 for (const auto &KV : Environment(property_environment))
4627 environment[KV.first()] = KV.second;
4629 return environment;
4632 void TargetProperties::SetEnvironment(Environment env) {
4633 // TODO: Get rid of the Args intermediate step
4634 const uint32_t idx = ePropertyEnvVars;
4635 m_collection_sp->SetPropertyAtIndexFromArgs(idx, Args(env));
4638 bool TargetProperties::GetSkipPrologue() const {
4639 const uint32_t idx = ePropertySkipPrologue;
4640 return GetPropertyAtIndexAs<bool>(
4641 idx, g_target_properties[idx].default_uint_value != 0);
4644 PathMappingList &TargetProperties::GetSourcePathMap() const {
4645 const uint32_t idx = ePropertySourceMap;
4646 OptionValuePathMappings *option_value =
4647 m_collection_sp->GetPropertyAtIndexAsOptionValuePathMappings(idx);
4648 assert(option_value);
4649 return option_value->GetCurrentValue();
4652 PathMappingList &TargetProperties::GetObjectPathMap() const {
4653 const uint32_t idx = ePropertyObjectMap;
4654 OptionValuePathMappings *option_value =
4655 m_collection_sp->GetPropertyAtIndexAsOptionValuePathMappings(idx);
4656 assert(option_value);
4657 return option_value->GetCurrentValue();
4660 bool TargetProperties::GetAutoSourceMapRelative() const {
4661 const uint32_t idx = ePropertyAutoSourceMapRelative;
4662 return GetPropertyAtIndexAs<bool>(
4663 idx, g_target_properties[idx].default_uint_value != 0);
4666 void TargetProperties::AppendExecutableSearchPaths(const FileSpec &dir) {
4667 const uint32_t idx = ePropertyExecutableSearchPaths;
4668 OptionValueFileSpecList *option_value =
4669 m_collection_sp->GetPropertyAtIndexAsOptionValueFileSpecList(idx);
4670 assert(option_value);
4671 option_value->AppendCurrentValue(dir);
4674 FileSpecList TargetProperties::GetExecutableSearchPaths() {
4675 const uint32_t idx = ePropertyExecutableSearchPaths;
4676 return GetPropertyAtIndexAs<FileSpecList>(idx, {});
4679 FileSpecList TargetProperties::GetDebugFileSearchPaths() {
4680 const uint32_t idx = ePropertyDebugFileSearchPaths;
4681 return GetPropertyAtIndexAs<FileSpecList>(idx, {});
4684 FileSpecList TargetProperties::GetClangModuleSearchPaths() {
4685 const uint32_t idx = ePropertyClangModuleSearchPaths;
4686 return GetPropertyAtIndexAs<FileSpecList>(idx, {});
4689 bool TargetProperties::GetEnableAutoImportClangModules() const {
4690 const uint32_t idx = ePropertyAutoImportClangModules;
4691 return GetPropertyAtIndexAs<bool>(
4692 idx, g_target_properties[idx].default_uint_value != 0);
4695 ImportStdModule TargetProperties::GetImportStdModule() const {
4696 const uint32_t idx = ePropertyImportStdModule;
4697 return GetPropertyAtIndexAs<ImportStdModule>(
4698 idx, static_cast<ImportStdModule>(
4699 g_target_properties[idx].default_uint_value));
4702 DynamicClassInfoHelper TargetProperties::GetDynamicClassInfoHelper() const {
4703 const uint32_t idx = ePropertyDynamicClassInfoHelper;
4704 return GetPropertyAtIndexAs<DynamicClassInfoHelper>(
4705 idx, static_cast<DynamicClassInfoHelper>(
4706 g_target_properties[idx].default_uint_value));
4709 bool TargetProperties::GetEnableAutoApplyFixIts() const {
4710 const uint32_t idx = ePropertyAutoApplyFixIts;
4711 return GetPropertyAtIndexAs<bool>(
4712 idx, g_target_properties[idx].default_uint_value != 0);
4715 uint64_t TargetProperties::GetNumberOfRetriesWithFixits() const {
4716 const uint32_t idx = ePropertyRetriesWithFixIts;
4717 return GetPropertyAtIndexAs<uint64_t>(
4718 idx, g_target_properties[idx].default_uint_value);
4721 bool TargetProperties::GetEnableNotifyAboutFixIts() const {
4722 const uint32_t idx = ePropertyNotifyAboutFixIts;
4723 return GetPropertyAtIndexAs<bool>(
4724 idx, g_target_properties[idx].default_uint_value != 0);
4727 FileSpec TargetProperties::GetSaveJITObjectsDir() const {
4728 const uint32_t idx = ePropertySaveObjectsDir;
4729 return GetPropertyAtIndexAs<FileSpec>(idx, {});
4732 void TargetProperties::CheckJITObjectsDir() {
4733 FileSpec new_dir = GetSaveJITObjectsDir();
4734 if (!new_dir)
4735 return;
4737 const FileSystem &instance = FileSystem::Instance();
4738 bool exists = instance.Exists(new_dir);
4739 bool is_directory = instance.IsDirectory(new_dir);
4740 std::string path = new_dir.GetPath(true);
4741 bool writable = llvm::sys::fs::can_write(path);
4742 if (exists && is_directory && writable)
4743 return;
4745 m_collection_sp->GetPropertyAtIndex(ePropertySaveObjectsDir)
4746 ->GetValue()
4747 ->Clear();
4749 std::string buffer;
4750 llvm::raw_string_ostream os(buffer);
4751 os << "JIT object dir '" << path << "' ";
4752 if (!exists)
4753 os << "does not exist";
4754 else if (!is_directory)
4755 os << "is not a directory";
4756 else if (!writable)
4757 os << "is not writable";
4759 std::optional<lldb::user_id_t> debugger_id;
4760 if (m_target)
4761 debugger_id = m_target->GetDebugger().GetID();
4762 Debugger::ReportError(buffer, debugger_id);
4765 bool TargetProperties::GetEnableSyntheticValue() const {
4766 const uint32_t idx = ePropertyEnableSynthetic;
4767 return GetPropertyAtIndexAs<bool>(
4768 idx, g_target_properties[idx].default_uint_value != 0);
4771 bool TargetProperties::ShowHexVariableValuesWithLeadingZeroes() const {
4772 const uint32_t idx = ePropertyShowHexVariableValuesWithLeadingZeroes;
4773 return GetPropertyAtIndexAs<bool>(
4774 idx, g_target_properties[idx].default_uint_value != 0);
4777 uint32_t TargetProperties::GetMaxZeroPaddingInFloatFormat() const {
4778 const uint32_t idx = ePropertyMaxZeroPaddingInFloatFormat;
4779 return GetPropertyAtIndexAs<uint64_t>(
4780 idx, g_target_properties[idx].default_uint_value);
4783 uint32_t TargetProperties::GetMaximumNumberOfChildrenToDisplay() const {
4784 const uint32_t idx = ePropertyMaxChildrenCount;
4785 return GetPropertyAtIndexAs<uint64_t>(
4786 idx, g_target_properties[idx].default_uint_value);
4789 std::pair<uint32_t, bool>
4790 TargetProperties::GetMaximumDepthOfChildrenToDisplay() const {
4791 const uint32_t idx = ePropertyMaxChildrenDepth;
4792 auto *option_value =
4793 m_collection_sp->GetPropertyAtIndexAsOptionValueUInt64(idx);
4794 bool is_default = !option_value->OptionWasSet();
4795 return {option_value->GetCurrentValue(), is_default};
4798 uint32_t TargetProperties::GetMaximumSizeOfStringSummary() const {
4799 const uint32_t idx = ePropertyMaxSummaryLength;
4800 return GetPropertyAtIndexAs<uint64_t>(
4801 idx, g_target_properties[idx].default_uint_value);
4804 uint32_t TargetProperties::GetMaximumMemReadSize() const {
4805 const uint32_t idx = ePropertyMaxMemReadSize;
4806 return GetPropertyAtIndexAs<uint64_t>(
4807 idx, g_target_properties[idx].default_uint_value);
4810 FileSpec TargetProperties::GetStandardInputPath() const {
4811 const uint32_t idx = ePropertyInputPath;
4812 return GetPropertyAtIndexAs<FileSpec>(idx, {});
4815 void TargetProperties::SetStandardInputPath(llvm::StringRef path) {
4816 const uint32_t idx = ePropertyInputPath;
4817 SetPropertyAtIndex(idx, path);
4820 FileSpec TargetProperties::GetStandardOutputPath() const {
4821 const uint32_t idx = ePropertyOutputPath;
4822 return GetPropertyAtIndexAs<FileSpec>(idx, {});
4825 void TargetProperties::SetStandardOutputPath(llvm::StringRef path) {
4826 const uint32_t idx = ePropertyOutputPath;
4827 SetPropertyAtIndex(idx, path);
4830 FileSpec TargetProperties::GetStandardErrorPath() const {
4831 const uint32_t idx = ePropertyErrorPath;
4832 return GetPropertyAtIndexAs<FileSpec>(idx, {});
4835 void TargetProperties::SetStandardErrorPath(llvm::StringRef path) {
4836 const uint32_t idx = ePropertyErrorPath;
4837 SetPropertyAtIndex(idx, path);
4840 SourceLanguage TargetProperties::GetLanguage() const {
4841 const uint32_t idx = ePropertyLanguage;
4842 return {GetPropertyAtIndexAs<LanguageType>(idx, {})};
4845 llvm::StringRef TargetProperties::GetExpressionPrefixContents() {
4846 const uint32_t idx = ePropertyExprPrefix;
4847 OptionValueFileSpec *file =
4848 m_collection_sp->GetPropertyAtIndexAsOptionValueFileSpec(idx);
4849 if (file) {
4850 DataBufferSP data_sp(file->GetFileContents());
4851 if (data_sp)
4852 return llvm::StringRef(
4853 reinterpret_cast<const char *>(data_sp->GetBytes()),
4854 data_sp->GetByteSize());
4856 return "";
4859 uint64_t TargetProperties::GetExprErrorLimit() const {
4860 const uint32_t idx = ePropertyExprErrorLimit;
4861 return GetPropertyAtIndexAs<uint64_t>(
4862 idx, g_target_properties[idx].default_uint_value);
4865 uint64_t TargetProperties::GetExprAllocAddress() const {
4866 const uint32_t idx = ePropertyExprAllocAddress;
4867 return GetPropertyAtIndexAs<uint64_t>(
4868 idx, g_target_properties[idx].default_uint_value);
4871 uint64_t TargetProperties::GetExprAllocSize() const {
4872 const uint32_t idx = ePropertyExprAllocSize;
4873 return GetPropertyAtIndexAs<uint64_t>(
4874 idx, g_target_properties[idx].default_uint_value);
4877 uint64_t TargetProperties::GetExprAllocAlign() const {
4878 const uint32_t idx = ePropertyExprAllocAlign;
4879 return GetPropertyAtIndexAs<uint64_t>(
4880 idx, g_target_properties[idx].default_uint_value);
4883 bool TargetProperties::GetBreakpointsConsultPlatformAvoidList() {
4884 const uint32_t idx = ePropertyBreakpointUseAvoidList;
4885 return GetPropertyAtIndexAs<bool>(
4886 idx, g_target_properties[idx].default_uint_value != 0);
4889 bool TargetProperties::GetUseHexImmediates() const {
4890 const uint32_t idx = ePropertyUseHexImmediates;
4891 return GetPropertyAtIndexAs<bool>(
4892 idx, g_target_properties[idx].default_uint_value != 0);
4895 bool TargetProperties::GetUseFastStepping() const {
4896 const uint32_t idx = ePropertyUseFastStepping;
4897 return GetPropertyAtIndexAs<bool>(
4898 idx, g_target_properties[idx].default_uint_value != 0);
4901 bool TargetProperties::GetDisplayExpressionsInCrashlogs() const {
4902 const uint32_t idx = ePropertyDisplayExpressionsInCrashlogs;
4903 return GetPropertyAtIndexAs<bool>(
4904 idx, g_target_properties[idx].default_uint_value != 0);
4907 LoadScriptFromSymFile TargetProperties::GetLoadScriptFromSymbolFile() const {
4908 const uint32_t idx = ePropertyLoadScriptFromSymbolFile;
4909 return GetPropertyAtIndexAs<LoadScriptFromSymFile>(
4910 idx, static_cast<LoadScriptFromSymFile>(
4911 g_target_properties[idx].default_uint_value));
4914 LoadCWDlldbinitFile TargetProperties::GetLoadCWDlldbinitFile() const {
4915 const uint32_t idx = ePropertyLoadCWDlldbinitFile;
4916 return GetPropertyAtIndexAs<LoadCWDlldbinitFile>(
4917 idx, static_cast<LoadCWDlldbinitFile>(
4918 g_target_properties[idx].default_uint_value));
4921 Disassembler::HexImmediateStyle TargetProperties::GetHexImmediateStyle() const {
4922 const uint32_t idx = ePropertyHexImmediateStyle;
4923 return GetPropertyAtIndexAs<Disassembler::HexImmediateStyle>(
4924 idx, static_cast<Disassembler::HexImmediateStyle>(
4925 g_target_properties[idx].default_uint_value));
4928 MemoryModuleLoadLevel TargetProperties::GetMemoryModuleLoadLevel() const {
4929 const uint32_t idx = ePropertyMemoryModuleLoadLevel;
4930 return GetPropertyAtIndexAs<MemoryModuleLoadLevel>(
4931 idx, static_cast<MemoryModuleLoadLevel>(
4932 g_target_properties[idx].default_uint_value));
4935 bool TargetProperties::GetUserSpecifiedTrapHandlerNames(Args &args) const {
4936 const uint32_t idx = ePropertyTrapHandlerNames;
4937 return m_collection_sp->GetPropertyAtIndexAsArgs(idx, args);
4940 void TargetProperties::SetUserSpecifiedTrapHandlerNames(const Args &args) {
4941 const uint32_t idx = ePropertyTrapHandlerNames;
4942 m_collection_sp->SetPropertyAtIndexFromArgs(idx, args);
4945 bool TargetProperties::GetDisplayRuntimeSupportValues() const {
4946 const uint32_t idx = ePropertyDisplayRuntimeSupportValues;
4947 return GetPropertyAtIndexAs<bool>(
4948 idx, g_target_properties[idx].default_uint_value != 0);
4951 void TargetProperties::SetDisplayRuntimeSupportValues(bool b) {
4952 const uint32_t idx = ePropertyDisplayRuntimeSupportValues;
4953 SetPropertyAtIndex(idx, b);
4956 bool TargetProperties::GetDisplayRecognizedArguments() const {
4957 const uint32_t idx = ePropertyDisplayRecognizedArguments;
4958 return GetPropertyAtIndexAs<bool>(
4959 idx, g_target_properties[idx].default_uint_value != 0);
4962 void TargetProperties::SetDisplayRecognizedArguments(bool b) {
4963 const uint32_t idx = ePropertyDisplayRecognizedArguments;
4964 SetPropertyAtIndex(idx, b);
4967 const ProcessLaunchInfo &TargetProperties::GetProcessLaunchInfo() const {
4968 return m_launch_info;
4971 void TargetProperties::SetProcessLaunchInfo(
4972 const ProcessLaunchInfo &launch_info) {
4973 m_launch_info = launch_info;
4974 SetArg0(launch_info.GetArg0());
4975 SetRunArguments(launch_info.GetArguments());
4976 SetEnvironment(launch_info.GetEnvironment());
4977 const FileAction *input_file_action =
4978 launch_info.GetFileActionForFD(STDIN_FILENO);
4979 if (input_file_action) {
4980 SetStandardInputPath(input_file_action->GetPath());
4982 const FileAction *output_file_action =
4983 launch_info.GetFileActionForFD(STDOUT_FILENO);
4984 if (output_file_action) {
4985 SetStandardOutputPath(output_file_action->GetPath());
4987 const FileAction *error_file_action =
4988 launch_info.GetFileActionForFD(STDERR_FILENO);
4989 if (error_file_action) {
4990 SetStandardErrorPath(error_file_action->GetPath());
4992 SetDetachOnError(launch_info.GetFlags().Test(lldb::eLaunchFlagDetachOnError));
4993 SetDisableASLR(launch_info.GetFlags().Test(lldb::eLaunchFlagDisableASLR));
4994 SetInheritTCC(
4995 launch_info.GetFlags().Test(lldb::eLaunchFlagInheritTCCFromParent));
4996 SetDisableSTDIO(launch_info.GetFlags().Test(lldb::eLaunchFlagDisableSTDIO));
4999 bool TargetProperties::GetRequireHardwareBreakpoints() const {
5000 const uint32_t idx = ePropertyRequireHardwareBreakpoints;
5001 return GetPropertyAtIndexAs<bool>(
5002 idx, g_target_properties[idx].default_uint_value != 0);
5005 void TargetProperties::SetRequireHardwareBreakpoints(bool b) {
5006 const uint32_t idx = ePropertyRequireHardwareBreakpoints;
5007 m_collection_sp->SetPropertyAtIndex(idx, b);
5010 bool TargetProperties::GetAutoInstallMainExecutable() const {
5011 const uint32_t idx = ePropertyAutoInstallMainExecutable;
5012 return GetPropertyAtIndexAs<bool>(
5013 idx, g_target_properties[idx].default_uint_value != 0);
5016 void TargetProperties::Arg0ValueChangedCallback() {
5017 m_launch_info.SetArg0(GetArg0());
5020 void TargetProperties::RunArgsValueChangedCallback() {
5021 Args args;
5022 if (GetRunArguments(args))
5023 m_launch_info.GetArguments() = args;
5026 void TargetProperties::EnvVarsValueChangedCallback() {
5027 m_launch_info.GetEnvironment() = ComputeEnvironment();
5030 void TargetProperties::InputPathValueChangedCallback() {
5031 m_launch_info.AppendOpenFileAction(STDIN_FILENO, GetStandardInputPath(), true,
5032 false);
5035 void TargetProperties::OutputPathValueChangedCallback() {
5036 m_launch_info.AppendOpenFileAction(STDOUT_FILENO, GetStandardOutputPath(),
5037 false, true);
5040 void TargetProperties::ErrorPathValueChangedCallback() {
5041 m_launch_info.AppendOpenFileAction(STDERR_FILENO, GetStandardErrorPath(),
5042 false, true);
5045 void TargetProperties::DetachOnErrorValueChangedCallback() {
5046 if (GetDetachOnError())
5047 m_launch_info.GetFlags().Set(lldb::eLaunchFlagDetachOnError);
5048 else
5049 m_launch_info.GetFlags().Clear(lldb::eLaunchFlagDetachOnError);
5052 void TargetProperties::DisableASLRValueChangedCallback() {
5053 if (GetDisableASLR())
5054 m_launch_info.GetFlags().Set(lldb::eLaunchFlagDisableASLR);
5055 else
5056 m_launch_info.GetFlags().Clear(lldb::eLaunchFlagDisableASLR);
5059 void TargetProperties::InheritTCCValueChangedCallback() {
5060 if (GetInheritTCC())
5061 m_launch_info.GetFlags().Set(lldb::eLaunchFlagInheritTCCFromParent);
5062 else
5063 m_launch_info.GetFlags().Clear(lldb::eLaunchFlagInheritTCCFromParent);
5066 void TargetProperties::DisableSTDIOValueChangedCallback() {
5067 if (GetDisableSTDIO())
5068 m_launch_info.GetFlags().Set(lldb::eLaunchFlagDisableSTDIO);
5069 else
5070 m_launch_info.GetFlags().Clear(lldb::eLaunchFlagDisableSTDIO);
5073 bool TargetProperties::GetDebugUtilityExpression() const {
5074 const uint32_t idx = ePropertyDebugUtilityExpression;
5075 return GetPropertyAtIndexAs<bool>(
5076 idx, g_target_properties[idx].default_uint_value != 0);
5079 void TargetProperties::SetDebugUtilityExpression(bool debug) {
5080 const uint32_t idx = ePropertyDebugUtilityExpression;
5081 SetPropertyAtIndex(idx, debug);
5084 // Target::TargetEventData
5086 Target::TargetEventData::TargetEventData(const lldb::TargetSP &target_sp)
5087 : EventData(), m_target_sp(target_sp), m_module_list() {}
5089 Target::TargetEventData::TargetEventData(const lldb::TargetSP &target_sp,
5090 const ModuleList &module_list)
5091 : EventData(), m_target_sp(target_sp), m_module_list(module_list) {}
5093 Target::TargetEventData::~TargetEventData() = default;
5095 llvm::StringRef Target::TargetEventData::GetFlavorString() {
5096 return "Target::TargetEventData";
5099 void Target::TargetEventData::Dump(Stream *s) const {
5100 for (size_t i = 0; i < m_module_list.GetSize(); ++i) {
5101 if (i != 0)
5102 *s << ", ";
5103 m_module_list.GetModuleAtIndex(i)->GetDescription(
5104 s->AsRawOstream(), lldb::eDescriptionLevelBrief);
5108 const Target::TargetEventData *
5109 Target::TargetEventData::GetEventDataFromEvent(const Event *event_ptr) {
5110 if (event_ptr) {
5111 const EventData *event_data = event_ptr->GetData();
5112 if (event_data &&
5113 event_data->GetFlavor() == TargetEventData::GetFlavorString())
5114 return static_cast<const TargetEventData *>(event_ptr->GetData());
5116 return nullptr;
5119 TargetSP Target::TargetEventData::GetTargetFromEvent(const Event *event_ptr) {
5120 TargetSP target_sp;
5121 const TargetEventData *event_data = GetEventDataFromEvent(event_ptr);
5122 if (event_data)
5123 target_sp = event_data->m_target_sp;
5124 return target_sp;
5127 ModuleList
5128 Target::TargetEventData::GetModuleListFromEvent(const Event *event_ptr) {
5129 ModuleList module_list;
5130 const TargetEventData *event_data = GetEventDataFromEvent(event_ptr);
5131 if (event_data)
5132 module_list = event_data->m_module_list;
5133 return module_list;
5136 std::recursive_mutex &Target::GetAPIMutex() {
5137 if (GetProcessSP() && GetProcessSP()->CurrentThreadIsPrivateStateThread())
5138 return m_private_mutex;
5139 else
5140 return m_mutex;
5143 /// Get metrics associated with this target in JSON format.
5144 llvm::json::Value
5145 Target::ReportStatistics(const lldb_private::StatisticsOptions &options) {
5146 return m_stats.ToJSON(*this, options);
5149 void Target::ResetStatistics() { m_stats.Reset(*this); }