Skip to content

Commit a7a5d22

Browse files
authored
Merge pull request #5133 from apple/🍒/rebranch/bd3976fed470+8d36a82d0a3d+11f45f36dcf5
🍒/rebranch/bd3976fed470+8d36a82d0a3d+11f45f36dcf5
2 parents 962469a + 188bfd2 commit a7a5d22

12 files changed

+331
-189
lines changed

lldb/include/lldb/Core/Debugger.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -82,6 +82,7 @@ class Debugger : public std::enable_shared_from_this<Debugger>,
8282
eBroadcastBitProgress = (1 << 0),
8383
eBroadcastBitWarning = (1 << 1),
8484
eBroadcastBitError = (1 << 2),
85+
eBroadcastSymbolChange = (1 << 3),
8586
};
8687

8788
static ConstString GetStaticBroadcasterClass();
@@ -438,6 +439,8 @@ class Debugger : public std::enable_shared_from_this<Debugger>,
438439
llvm::Optional<lldb::user_id_t> debugger_id = llvm::None,
439440
std::once_flag *once = nullptr);
440441

442+
static void ReportSymbolChange(const ModuleSpec &module_spec);
443+
441444
protected:
442445
friend class CommandInterpreter;
443446
friend class SwiftREPL;

lldb/include/lldb/Core/DebuggerEvents.h

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
//
77
//===----------------------------------------------------------------------===//
88

9+
#include "lldb/Core/ModuleSpec.h"
910
#include "lldb/Utility/ConstString.h"
1011
#include "lldb/Utility/Event.h"
1112

@@ -82,6 +83,28 @@ class DiagnosticEventData : public EventData {
8283
const DiagnosticEventData &operator=(const DiagnosticEventData &) = delete;
8384
};
8485

86+
class SymbolChangeEventData : public EventData {
87+
public:
88+
SymbolChangeEventData(lldb::DebuggerWP debugger_wp, ModuleSpec module_spec)
89+
: m_debugger_wp(debugger_wp), m_module_spec(std::move(module_spec)) {}
90+
91+
static ConstString GetFlavorString();
92+
ConstString GetFlavor() const override;
93+
94+
static const SymbolChangeEventData *
95+
GetEventDataFromEvent(const Event *event_ptr);
96+
97+
void DoOnRemoval(Event *event_ptr) override;
98+
99+
private:
100+
lldb::DebuggerWP m_debugger_wp;
101+
ModuleSpec m_module_spec;
102+
103+
SymbolChangeEventData(const SymbolChangeEventData &) = delete;
104+
const SymbolChangeEventData &
105+
operator=(const SymbolChangeEventData &) = delete;
106+
};
107+
85108
} // namespace lldb_private
86109

87110
#endif // LLDB_CORE_DEBUGGER_EVENTS_H

lldb/include/lldb/Core/ModuleList.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -71,6 +71,7 @@ class ModuleListProperties : public Properties {
7171
bool SetClangModulesCachePath(const FileSpec &path);
7272
bool GetEnableExternalLookup() const;
7373
bool SetEnableExternalLookup(bool new_value);
74+
bool GetEnableBackgroundLookup() const;
7475
bool GetEnableLLDBIndexCache() const;
7576
bool SetEnableLLDBIndexCache(bool new_value);
7677
uint64_t GetLLDBIndexCacheMaxByteSize();
@@ -466,6 +467,8 @@ class ModuleList {
466467
static void FindSharedModules(const ModuleSpec &module_spec,
467468
ModuleList &matching_module_list);
468469

470+
static lldb::ModuleSP FindSharedModule(const UUID &uuid);
471+
469472
static size_t RemoveOrphanSharedModules(bool mandatory);
470473

471474
static bool RemoveSharedModuleIfOrphaned(const Module *module_ptr);

lldb/include/lldb/Symbol/LocateSymbolFile.h

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@
1414
#include "lldb/Core/FileSpecList.h"
1515
#include "lldb/Utility/FileSpec.h"
1616
#include "lldb/Utility/Status.h"
17+
#include "lldb/lldb-forward.h"
1718

1819
namespace lldb_private {
1920

@@ -52,7 +53,15 @@ class Symbols {
5253
//
5354
static bool DownloadObjectAndSymbolFile(ModuleSpec &module_spec,
5455
Status &error,
55-
bool force_lookup = true);
56+
bool force_lookup = true,
57+
bool copy_executable = true);
58+
59+
/// Locate the symbol file for the given UUID on a background thread. This
60+
/// function returns immediately. Under the hood it uses the debugger's
61+
/// thread pool to call DownloadObjectAndSymbolFile. If a symbol file is
62+
/// found, this will notify all target which contain the module with the
63+
/// given UUID.
64+
static void DownloadSymbolFileAsync(const UUID &uuid);
5665
};
5766

5867
} // namespace lldb_private

lldb/include/lldb/Target/Target.h

Lines changed: 15 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -207,7 +207,7 @@ class TargetProperties : public Properties {
207207
bool GetEnableNotifyAboutFixIts() const;
208208

209209
FileSpec GetSaveJITObjectsDir() const;
210-
210+
211211
bool GetEnableSyntheticValue() const;
212212

213213
uint32_t GetMaxZeroPaddingInFloatFormat() const;
@@ -305,7 +305,7 @@ class TargetProperties : public Properties {
305305
void DisableASLRValueChangedCallback();
306306
void InheritTCCValueChangedCallback();
307307
void DisableSTDIOValueChangedCallback();
308-
308+
309309
// Settings checker for target.jit-save-objects-dir:
310310
void CheckJITObjectsDir();
311311

@@ -543,7 +543,8 @@ class Target : public std::enable_shared_from_this<Target>,
543543
eBroadcastBitModulesLoaded = (1 << 1),
544544
eBroadcastBitModulesUnloaded = (1 << 2),
545545
eBroadcastBitWatchpointChanged = (1 << 3),
546-
eBroadcastBitSymbolsLoaded = (1 << 4)
546+
eBroadcastBitSymbolsLoaded = (1 << 4),
547+
eBroadcastBitSymbolsChanged = (1 << 5),
547548
};
548549

549550
// These two functions fill out the Broadcaster interface:
@@ -1045,7 +1046,7 @@ class Target : public std::enable_shared_from_this<Target>,
10451046
ModuleIsExcludedForUnconstrainedSearches(const lldb::ModuleSP &module_sp);
10461047

10471048
const ArchSpec &GetArchitecture() const { return m_arch.GetSpec(); }
1048-
1049+
10491050
/// Returns the name of the target's ABI plugin.
10501051
llvm::StringRef GetABIName() const;
10511052

@@ -1535,30 +1536,30 @@ class Target : public std::enable_shared_from_this<Target>,
15351536
LazyBool pass = eLazyBoolCalculate;
15361537
LazyBool notify = eLazyBoolCalculate;
15371538
LazyBool stop = eLazyBoolCalculate;
1538-
DummySignalValues(LazyBool pass, LazyBool notify, LazyBool stop) :
1539-
pass(pass), notify(notify), stop(stop) {}
1539+
DummySignalValues(LazyBool pass, LazyBool notify, LazyBool stop)
1540+
: pass(pass), notify(notify), stop(stop) {}
15401541
DummySignalValues() = default;
15411542
};
15421543
using DummySignalElement = llvm::StringMapEntry<DummySignalValues>;
1543-
static bool UpdateSignalFromDummy(lldb::UnixSignalsSP signals_sp,
1544-
const DummySignalElement &element);
1545-
static bool ResetSignalFromDummy(lldb::UnixSignalsSP signals_sp,
1546-
const DummySignalElement &element);
1544+
static bool UpdateSignalFromDummy(lldb::UnixSignalsSP signals_sp,
1545+
const DummySignalElement &element);
1546+
static bool ResetSignalFromDummy(lldb::UnixSignalsSP signals_sp,
1547+
const DummySignalElement &element);
15471548

15481549
public:
15491550
/// Add a signal to the Target's list of stored signals/actions. These
15501551
/// values will get copied into any processes launched from
15511552
/// this target.
1552-
void AddDummySignal(llvm::StringRef name, LazyBool pass, LazyBool print,
1553+
void AddDummySignal(llvm::StringRef name, LazyBool pass, LazyBool print,
15531554
LazyBool stop);
15541555
/// Updates the signals in signals_sp using the stored dummy signals.
15551556
/// If warning_stream_sp is not null, if any stored signals are not found in
15561557
/// the current process, a warning will be emitted here.
1557-
void UpdateSignalsFromDummy(lldb::UnixSignalsSP signals_sp,
1558+
void UpdateSignalsFromDummy(lldb::UnixSignalsSP signals_sp,
15581559
lldb::StreamSP warning_stream_sp);
15591560
/// Clear the dummy signals in signal_names from the target, or all signals
15601561
/// if signal_names is empty. Also remove the behaviors they set from the
1561-
/// process's signals if it exists.
1562+
/// process's signals if it exists.
15621563
void ClearDummySignals(Args &signal_names);
15631564
/// Print all the signals set in this target.
15641565
void PrintDummySignals(Stream &strm, Args &signals);
@@ -1644,7 +1645,7 @@ class Target : public std::enable_shared_from_this<Target>,
16441645
lldb::TraceSP m_trace_sp;
16451646
/// Stores the frame recognizers of this target.
16461647
lldb::StackFrameRecognizerManagerUP m_frame_recognizer_manager_up;
1647-
/// These are used to set the signal state when you don't have a process and
1648+
/// These are used to set the signal state when you don't have a process and
16481649
/// more usefully in the Dummy target where you can't know exactly what
16491650
/// signals you will have.
16501651
llvm::StringMap<DummySignalValues> m_dummy_signals;

lldb/source/Core/CoreProperties.td

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,10 @@ let Definition = "modulelist" in {
55
Global,
66
DefaultTrue,
77
Desc<"Control the use of external tools and repositories to locate symbol files. Directories listed in target.debug-file-search-paths and directory of the executable are always checked first for separate debug info files. Then depending on this setting: On macOS, Spotlight would be also used to locate a matching .dSYM bundle based on the UUID of the executable. On NetBSD, directory /usr/libdata/debug would be also searched. On platforms other than NetBSD directory /usr/lib/debug would be also searched.">;
8+
def EnableBackgroundLookup: Property<"enable-background-lookup", "Boolean">,
9+
Global,
10+
DefaultFalse,
11+
Desc<"On macOS, enable calling dsymForUUID (or an equivalent script/binary) in the background to locate symbol files that weren't found.">;
812
def ClangModulesCachePath: Property<"clang-modules-cache-path", "FileSpec">,
913
Global,
1014
DefaultStringValue<"">,

lldb/source/Core/Debugger.cpp

Lines changed: 24 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313
#include "lldb/Core/FormatEntity.h"
1414
#include "lldb/Core/Mangled.h"
1515
#include "lldb/Core/ModuleList.h"
16+
#include "lldb/Core/ModuleSpec.h"
1617
#include "lldb/Core/PluginManager.h"
1718
#include "lldb/Core/StreamAsynchronousIO.h"
1819
#include "lldb/Core/StreamFile.h"
@@ -104,6 +105,7 @@ static std::recursive_mutex *g_debugger_list_mutex_ptr =
104105
nullptr; // NOTE: intentional leak to avoid issues with C++ destructor chain
105106
static DebuggerList *g_debugger_list_ptr =
106107
nullptr; // NOTE: intentional leak to avoid issues with C++ destructor chain
108+
static llvm::ThreadPool *g_thread_pool = nullptr;
107109

108110
static constexpr OptionEnumValueElement g_show_disassembly_enum_values[] = {
109111
{
@@ -538,13 +540,19 @@ void Debugger::Initialize(LoadPluginCallbackType load_plugin_callback) {
538540
"Debugger::Initialize called more than once!");
539541
g_debugger_list_mutex_ptr = new std::recursive_mutex();
540542
g_debugger_list_ptr = new DebuggerList();
543+
g_thread_pool = new llvm::ThreadPool(llvm::optimal_concurrency());
541544
g_load_plugin_callback = load_plugin_callback;
542545
}
543546

544547
void Debugger::Terminate() {
545548
assert(g_debugger_list_ptr &&
546549
"Debugger::Terminate called without a matching Debugger::Initialize!");
547550

551+
if (g_thread_pool) {
552+
// The destructor will wait for all the threads to complete.
553+
delete g_thread_pool;
554+
}
555+
548556
if (g_debugger_list_ptr && g_debugger_list_mutex_ptr) {
549557
// Clear our global list of debugger objects
550558
{
@@ -1445,6 +1453,18 @@ void Debugger::ReportError(std::string message,
14451453
debugger_id, once);
14461454
}
14471455

1456+
void Debugger::ReportSymbolChange(const ModuleSpec &module_spec) {
1457+
if (g_debugger_list_ptr && g_debugger_list_mutex_ptr) {
1458+
std::lock_guard<std::recursive_mutex> guard(*g_debugger_list_mutex_ptr);
1459+
for (DebuggerSP debugger_sp : *g_debugger_list_ptr) {
1460+
EventSP event_sp = std::make_shared<Event>(
1461+
Debugger::eBroadcastSymbolChange,
1462+
new SymbolChangeEventData(debugger_sp, module_spec));
1463+
debugger_sp->GetBroadcaster().BroadcastEvent(event_sp);
1464+
}
1465+
}
1466+
}
1467+
14481468
static std::shared_ptr<LogHandler>
14491469
CreateLogHandler(LogHandlerKind log_handler_kind, int fd, bool should_close,
14501470
size_t buffer_size) {
@@ -1754,8 +1774,8 @@ lldb::thread_result_t Debugger::DefaultEventHandler() {
17541774
CommandInterpreter::eBroadcastBitAsynchronousErrorData);
17551775

17561776
listener_sp->StartListeningForEvents(
1757-
&m_broadcaster,
1758-
eBroadcastBitProgress | eBroadcastBitWarning | eBroadcastBitError);
1777+
&m_broadcaster, eBroadcastBitProgress | eBroadcastBitWarning |
1778+
eBroadcastBitError | eBroadcastSymbolChange);
17591779

17601780
// Let the thread that spawned us know that we have started up and that we
17611781
// are now listening to all required events so no events get missed
@@ -2057,11 +2077,7 @@ Status Debugger::RunREPL(LanguageType language, const char *repl_options) {
20572077
}
20582078

20592079
llvm::ThreadPool &Debugger::GetThreadPool() {
2060-
// NOTE: intentional leak to avoid issues with C++ destructor chain
2061-
static llvm::ThreadPool *g_thread_pool = nullptr;
2062-
static llvm::once_flag g_once_flag;
2063-
llvm::call_once(g_once_flag, []() {
2064-
g_thread_pool = new llvm::ThreadPool(llvm::optimal_concurrency());
2065-
});
2080+
assert(g_thread_pool &&
2081+
"Debugger::GetThreadPool called before Debugger::Initialize");
20662082
return *g_thread_pool;
20672083
}

lldb/source/Core/DebuggerEvents.cpp

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,9 +7,12 @@
77
//===----------------------------------------------------------------------===//
88

99
#include "lldb/Core/DebuggerEvents.h"
10+
#include "lldb/Core/Debugger.h"
11+
#include "lldb/Core/Module.h"
1012
#include "llvm/Support/WithColor.h"
1113

1214
using namespace lldb_private;
15+
using namespace lldb;
1316

1417
template <typename T>
1518
static const T *GetEventDataFromEventImpl(const Event *event_ptr) {
@@ -79,3 +82,37 @@ const DiagnosticEventData *
7982
DiagnosticEventData::GetEventDataFromEvent(const Event *event_ptr) {
8083
return GetEventDataFromEventImpl<DiagnosticEventData>(event_ptr);
8184
}
85+
86+
ConstString SymbolChangeEventData::GetFlavorString() {
87+
static ConstString g_flavor("SymbolChangeEventData");
88+
return g_flavor;
89+
}
90+
91+
ConstString SymbolChangeEventData::GetFlavor() const {
92+
return SymbolChangeEventData::GetFlavorString();
93+
}
94+
95+
const SymbolChangeEventData *
96+
SymbolChangeEventData::GetEventDataFromEvent(const Event *event_ptr) {
97+
return GetEventDataFromEventImpl<SymbolChangeEventData>(event_ptr);
98+
}
99+
100+
void SymbolChangeEventData::DoOnRemoval(Event *event_ptr) {
101+
DebuggerSP debugger_sp(m_debugger_wp.lock());
102+
if (!debugger_sp)
103+
return;
104+
105+
for (TargetSP target_sp : debugger_sp->GetTargetList().Targets()) {
106+
if (ModuleSP module_sp =
107+
target_sp->GetImages().FindModule(m_module_spec.GetUUID())) {
108+
{
109+
std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
110+
if (!module_sp->GetSymbolFileFileSpec())
111+
module_sp->SetSymbolFileFileSpec(m_module_spec.GetSymbolFileSpec());
112+
}
113+
ModuleList module_list;
114+
module_list.Append(module_sp);
115+
target_sp->SymbolsDidLoad(module_list);
116+
}
117+
}
118+
}

lldb/source/Core/Module.cpp

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@
2424
#include "lldb/Interpreter/ScriptInterpreter.h"
2525
#include "lldb/Symbol/CompileUnit.h"
2626
#include "lldb/Symbol/Function.h"
27+
#include "lldb/Symbol/LocateSymbolFile.h"
2728
#include "lldb/Symbol/ObjectFile.h"
2829
#include "lldb/Symbol/Symbol.h"
2930
#include "lldb/Symbol/SymbolContext.h"
@@ -1362,8 +1363,11 @@ void Module::SectionFileAddressesChanged() {
13621363
}
13631364

13641365
UnwindTable &Module::GetUnwindTable() {
1365-
if (!m_unwind_table)
1366+
if (!m_unwind_table) {
13661367
m_unwind_table.emplace(*this);
1368+
if (!m_symfile_spec)
1369+
Symbols::DownloadSymbolFileAsync(GetUUID());
1370+
}
13671371
return *m_unwind_table;
13681372
}
13691373

lldb/source/Core/ModuleList.cpp

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -130,6 +130,12 @@ bool ModuleListProperties::SetEnableExternalLookup(bool new_value) {
130130
nullptr, ePropertyEnableExternalLookup, new_value);
131131
}
132132

133+
bool ModuleListProperties::GetEnableBackgroundLookup() const {
134+
const uint32_t idx = ePropertyEnableBackgroundLookup;
135+
return m_collection_sp->GetPropertyAtIndexAsBoolean(
136+
nullptr, idx, g_modulelist_properties[idx].default_uint_value != 0);
137+
}
138+
133139
FileSpec ModuleListProperties::GetClangModulesCachePath() const {
134140
return m_collection_sp
135141
->GetPropertyAtIndexAsOptionValueFileSpec(nullptr, false,
@@ -925,6 +931,10 @@ void ModuleList::FindSharedModules(const ModuleSpec &module_spec,
925931
GetSharedModuleList().FindModules(module_spec, matching_module_list);
926932
}
927933

934+
lldb::ModuleSP ModuleList::FindSharedModule(const UUID &uuid) {
935+
return GetSharedModuleList().FindModule(uuid);
936+
}
937+
928938
size_t ModuleList::RemoveOrphanSharedModules(bool mandatory) {
929939
return GetSharedModuleList().RemoveOrphans(mandatory);
930940
}

0 commit comments

Comments
 (0)