Skip to content

Add support for inline DWARF source files. #75880

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Jan 4, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
23 changes: 16 additions & 7 deletions lldb/include/lldb/Symbol/CompileUnit.h
Original file line number Diff line number Diff line change
Expand Up @@ -112,10 +112,13 @@ class CompileUnit : public std::enable_shared_from_this<CompileUnit>,
/// the compile unit is optimized will be made when
/// CompileUnit::GetIsOptimized() is called.
///
/// \param[in] support_files
/// An rvalue list of already parsed support files.
/// \see lldb::LanguageType
CompileUnit(const lldb::ModuleSP &module_sp, void *user_data,
const FileSpec &file_spec, lldb::user_id_t uid,
lldb::LanguageType language, lldb_private::LazyBool is_optimized);
lldb::LanguageType language, lldb_private::LazyBool is_optimized,
SupportFileList &&support_files = {});

/// Add a function to this compile unit.
///
Expand Down Expand Up @@ -226,6 +229,9 @@ class CompileUnit : public std::enable_shared_from_this<CompileUnit>,
/// Return the primary source file associated with this compile unit.
const FileSpec &GetPrimaryFile() const { return m_file_spec; }

/// Return the primary source file associated with this compile unit.
void SetPrimaryFile(const FileSpec &fs) { m_file_spec = fs; }

/// Get the line table for the compile unit.
///
/// Called by clients and the SymbolFile plug-in. The SymbolFile plug-ins
Expand Down Expand Up @@ -265,7 +271,13 @@ class CompileUnit : public std::enable_shared_from_this<CompileUnit>,
///
/// \return
/// A support file list object.
const FileSpecList &GetSupportFiles();
const SupportFileList &GetSupportFiles();

/// Used by plugins that parse the support file list.
SupportFileList &GetSupportFileList() {
m_flags.Set(flagsParsedSupportFiles);
return m_support_files;
}

/// Get the compile unit's imported module list.
///
Expand Down Expand Up @@ -331,8 +343,6 @@ class CompileUnit : public std::enable_shared_from_this<CompileUnit>,
/// A line table object pointer that this object now owns.
void SetLineTable(LineTable *line_table);

void SetSupportFiles(FileSpecList support_files);

void SetDebugMacros(const DebugMacrosSP &debug_macros);

/// Set accessor for the variable list.
Expand Down Expand Up @@ -410,9 +420,8 @@ class CompileUnit : public std::enable_shared_from_this<CompileUnit>,
std::vector<SourceModule> m_imported_modules;
/// The primary file associated with this compile unit.
FileSpec m_file_spec;
/// Files associated with this compile unit's line table and
/// declarations.
FileSpecList m_support_files;
/// Files associated with this compile unit's line table and declarations.
SupportFileList m_support_files;
/// Line table that will get parsed on demand.
std::unique_ptr<LineTable> m_line_table_up;
/// Debug macros that will get parsed on demand.
Expand Down
2 changes: 1 addition & 1 deletion lldb/include/lldb/Symbol/SymbolFile.h
Original file line number Diff line number Diff line change
Expand Up @@ -197,7 +197,7 @@ class SymbolFile : public PluginInterface {
return false;
}
virtual bool ParseSupportFiles(CompileUnit &comp_unit,
FileSpecList &support_files) = 0;
SupportFileList &support_files) = 0;
virtual size_t ParseTypes(CompileUnit &comp_unit) = 0;
virtual bool ParseIsOptimized(CompileUnit &comp_unit) { return false; }

Expand Down
2 changes: 1 addition & 1 deletion lldb/include/lldb/Symbol/SymbolFileOnDemand.h
Original file line number Diff line number Diff line change
Expand Up @@ -81,7 +81,7 @@ class SymbolFileOnDemand : public lldb_private::SymbolFile {
llvm::function_ref<bool(lldb_private::Module &)>) override;

bool ParseSupportFiles(lldb_private::CompileUnit &comp_unit,
lldb_private::FileSpecList &support_files) override;
lldb_private::SupportFileList &support_files) override;

bool ParseIsOptimized(lldb_private::CompileUnit &comp_unit) override;

Expand Down
106 changes: 80 additions & 26 deletions lldb/include/lldb/Utility/FileSpecList.h
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,86 @@
namespace lldb_private {
class Stream;

/// Wraps either a FileSpec that represents a local file or a source
/// file whose contents is known (for example because it can be
/// reconstructed from debug info), but that hasn't been written to a
/// file yet.
class SupportFile {
protected:
FileSpec m_file_spec;

public:
SupportFile(const FileSpec &spec) : m_file_spec(spec) {}
SupportFile(const SupportFile &other) = delete;
SupportFile(SupportFile &&other) = default;
virtual ~SupportFile() = default;
bool operator==(const SupportFile &other) {
return m_file_spec == other.m_file_spec;
}
/// Return the file name only. Useful for resolving breakpoints by file name.
const FileSpec &GetSpecOnly() const { return m_file_spec; };
/// Materialize the file to disk and return the path to that temporary file.
virtual const FileSpec &Materialize() { return m_file_spec; }
};

/// A list of support files for a CompileUnit.
class SupportFileList {
public:
SupportFileList(){};
SupportFileList(const SupportFileList &) = delete;
SupportFileList(SupportFileList &&other) = default;

typedef std::vector<std::unique_ptr<SupportFile>> collection;
typedef collection::const_iterator const_iterator;
const_iterator begin() const { return m_files.begin(); }
const_iterator end() const { return m_files.end(); }

void Append(const FileSpec &file) {
return Append(std::make_unique<SupportFile>(file));
}
void Append(std::unique_ptr<SupportFile> &&file) {
m_files.push_back(std::move(file));
}
// FIXME: Only used by SymbolFilePDB. Replace with a DenseSet at call site.
bool AppendIfUnique(const FileSpec &file);
size_t GetSize() const { return m_files.size(); }
const FileSpec &GetFileSpecAtIndex(size_t idx) const;
size_t FindFileIndex(size_t idx, const FileSpec &file, bool full) const;
/// Find a compatible file index.
///
/// Find the index of a compatible file in the file spec list that matches \a
/// file starting \a idx entries into the file spec list. A file is considered
/// compatible if:
/// - The file matches exactly (only filename if \a file has no directory)
/// - If \a file is relative and any file in the list has this same suffix
/// - If any file in the list is relative and the relative path is a suffix
/// of \a file
///
/// This is used to implement better matching for setting breakpoints in
/// source files where an IDE might specify a full path when setting the
/// breakpoint and debug info contains relative paths, if a user specifies
/// a relative path when setting a breakpoint.
///
/// \param[in] idx
/// An index into the file list.
///
/// \param[in] file
/// The file specification to search for.
///
/// \return
/// The index of the file that matches \a file if it is found,
/// else UINT32_MAX is returned.
size_t FindCompatibleIndex(size_t idx, const FileSpec &file) const;

template <class... Args> void EmplaceBack(Args &&...args) {
m_files.push_back(
std::make_unique<SupportFile>(FileSpec(std::forward<Args>(args)...)));
}

protected:
collection m_files; ///< A collection of FileSpec objects.
};

/// \class FileSpecList FileSpecList.h "lldb/Utility/FileSpecList.h"
/// A file collection class.
///
Expand Down Expand Up @@ -114,32 +194,6 @@ class FileSpecList {
/// else UINT32_MAX is returned.
size_t FindFileIndex(size_t idx, const FileSpec &file, bool full) const;

/// Find a compatible file index.
///
/// Find the index of a compatible file in the file spec list that matches \a
/// file starting \a idx entries into the file spec list. A file is considered
/// compatible if:
/// - The file matches exactly (only filename if \a file has no directory)
/// - If \a file is relative and any file in the list has this same suffix
/// - If any file in the list is relative and the relative path is a suffix
/// of \a file
///
/// This is used to implement better matching for setting breakpoints in
/// source files where an IDE might specify a full path when setting the
/// breakpoint and debug info contains relative paths, if a user specifies
/// a relative path when setting a breakpoint.
///
/// \param[in] idx
/// An index into the file list.
///
/// \param[in] file
/// The file specification to search for.
///
/// \return
/// The index of the file that matches \a file if it is found,
/// else UINT32_MAX is returned.
size_t FindCompatibleIndex(size_t idx, const FileSpec &file) const;

/// Get file at index.
///
/// Gets a file from the file list. If \a idx is not a valid index, an empty
Expand Down
2 changes: 1 addition & 1 deletion lldb/source/API/SBCompileUnit.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -171,7 +171,7 @@ uint32_t SBCompileUnit::FindSupportFileIndex(uint32_t start_idx,
LLDB_INSTRUMENT_VA(this, start_idx, sb_file, full);

if (m_opaque_ptr) {
const FileSpecList &support_files = m_opaque_ptr->GetSupportFiles();
const SupportFileList &support_files = m_opaque_ptr->GetSupportFiles();
return support_files.FindFileIndex(start_idx, sb_file.ref(), full);
}
return 0;
Expand Down
2 changes: 1 addition & 1 deletion lldb/source/Commands/CommandObjectSource.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -204,7 +204,7 @@ class CommandObjectSourceInfo : public CommandObjectParsed {
if (cu) {
assert(file_spec.GetFilename().AsCString());
bool has_path = (file_spec.GetDirectory().AsCString() != nullptr);
const FileSpecList &cu_file_list = cu->GetSupportFiles();
const SupportFileList &cu_file_list = cu->GetSupportFiles();
size_t file_idx = cu_file_list.FindFileIndex(0, file_spec, has_path);
if (file_idx != UINT32_MAX) {
// Update the file to how it appears in the CU.
Expand Down
2 changes: 1 addition & 1 deletion lldb/source/Core/ModuleList.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -164,7 +164,7 @@ void ModuleListProperties::UpdateSymlinkMappings() {
llvm::sys::ScopedWriter lock(m_symlink_paths_mutex);
const bool notify = false;
m_symlink_paths.Clear(notify);
for (FileSpec symlink : list) {
for (auto symlink : list) {
FileSpec resolved;
Status status = FileSystem::Instance().Readlink(symlink, resolved);
if (status.Success())
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -488,18 +488,18 @@ CppModuleConfiguration GetModuleConfig(lldb::LanguageType language,

// Build a list of files we need to analyze to build the configuration.
FileSpecList files;
for (const FileSpec &f : sc.comp_unit->GetSupportFiles())
files.AppendIfUnique(f);
for (auto &f : sc.comp_unit->GetSupportFiles())
files.AppendIfUnique(f->Materialize());
// We also need to look at external modules in the case of -gmodules as they
// contain the support files for libc++ and the C library.
llvm::DenseSet<SymbolFile *> visited_symbol_files;
sc.comp_unit->ForEachExternalModule(
visited_symbol_files, [&files](Module &module) {
for (std::size_t i = 0; i < module.GetNumCompileUnits(); ++i) {
const FileSpecList &support_files =
const SupportFileList &support_files =
module.GetCompileUnitAtIndex(i)->GetSupportFiles();
for (const FileSpec &f : support_files) {
files.AppendIfUnique(f);
for (auto &f : support_files) {
files.AppendIfUnique(f->Materialize());
}
}
return false;
Expand All @@ -508,7 +508,7 @@ CppModuleConfiguration GetModuleConfig(lldb::LanguageType language,
LLDB_LOG(log, "[C++ module config] Found {0} support files to analyze",
files.GetSize());
if (log && log->GetVerbose()) {
for (const FileSpec &f : files)
for (auto &f : files)
LLDB_LOGV(log, "[C++ module config] Analyzing support file: {0}",
f.GetPath());
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -134,9 +134,9 @@ bool CppModuleConfiguration::hasValidConfig() {
CppModuleConfiguration::CppModuleConfiguration(
const FileSpecList &support_files, const llvm::Triple &triple) {
// Analyze all files we were given to build the configuration.
bool error = !llvm::all_of(support_files,
std::bind(&CppModuleConfiguration::analyzeFile,
this, std::placeholders::_1, triple));
bool error = !llvm::all_of(support_files, [&](auto &file) {
return CppModuleConfiguration::analyzeFile(file, triple);
});
// If we have a valid configuration at this point, set the
// include directories and module list that should be used.
if (!error && hasValidConfig()) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -278,13 +278,14 @@ bool SymbolFileBreakpad::ParseLineTable(CompileUnit &comp_unit) {
}

bool SymbolFileBreakpad::ParseSupportFiles(CompileUnit &comp_unit,
FileSpecList &support_files) {
SupportFileList &support_files) {
std::lock_guard<std::recursive_mutex> guard(GetModuleMutex());
CompUnitData &data = m_cu_data->GetEntryRef(comp_unit.GetID()).data;
if (!data.support_files)
ParseLineTableAndSupportFiles(comp_unit, data);

support_files = std::move(*data.support_files);
for (auto &fs : *data.support_files)
support_files.Append(fs);
return true;
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -73,7 +73,7 @@ class SymbolFileBreakpad : public SymbolFileCommon {
bool ParseDebugMacros(CompileUnit &comp_unit) override { return false; }

bool ParseSupportFiles(CompileUnit &comp_unit,
FileSpecList &support_files) override;
SupportFileList &support_files) override;
size_t ParseTypes(CompileUnit &cu) override { return 0; }

bool ParseImportedModules(
Expand Down Expand Up @@ -195,7 +195,6 @@ class SymbolFileBreakpad : public SymbolFileCommon {
Bookmark bookmark;
std::optional<FileSpecList> support_files;
std::unique_ptr<LineTable> line_table_up;

};

uint32_t CalculateNumCompileUnits() override;
Expand Down
2 changes: 1 addition & 1 deletion lldb/source/Plugins/SymbolFile/CTF/SymbolFileCTF.h
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,7 @@ class SymbolFileCTF : public lldb_private::SymbolFileCommon {
bool ParseDebugMacros(CompileUnit &comp_unit) override { return false; }

bool ParseSupportFiles(CompileUnit &comp_unit,
FileSpecList &support_files) override {
SupportFileList &support_files) override {
return false;
}

Expand Down
Loading