JDevlieghere created this revision.
JDevlieghere added reviewers: labath, arphaman, aprantl.
JDevlieghere added a project: LLDB.
Herald added subscribers: teemperor, abidh, dexonsmith, hiraditya, mgorny.
JDevlieghere added a parent revision: D76671: [FileCollector] Add a method to
add a whole directory and it contents..
The FileCollector in LLDB collects every files that's used during a debug
session when capture is enabled. This ensures that the reproducer only contains
the files necessary to reproduce. This approach is not a good fit for the dSYM
bundle, which is a directory on disk, but should be treated as a single unit.
On macOS LLDB have automatically find the matching dSYM for a binary by its
UUID. Having a incomplete dSYM in a reproducer can break debugging even when
reproducers are disabled.
This patch adds a custom FileCollector to LLDB that is aware of dSYM. When it
encounters a dSYM bundle, it iterates over everything inside it and adds it to
the reproducer. While this might seem like overkill right now, having custom
FileCollector is going to be inevitable as soon as we want to be smarter in
what we include in the reproducer. For example, to keep its size small, we
might want to skip system libraries in the future.
Repository:
rLLDB LLDB
https://reviews.llvm.org/D76672
Files:
lldb/include/lldb/Host/FileSystem.h
lldb/include/lldb/Utility/FileCollector.h
lldb/include/lldb/Utility/Reproducer.h
lldb/source/Utility/CMakeLists.txt
lldb/source/Utility/FileCollector.cpp
lldb/test/Shell/Reproducer/TestDSYM.test
llvm/include/llvm/Support/FileCollector.h
llvm/lib/Support/FileCollector.cpp
Index: llvm/lib/Support/FileCollector.cpp
===================================================================
--- llvm/lib/Support/FileCollector.cpp
+++ llvm/lib/Support/FileCollector.cpp
@@ -61,26 +61,25 @@
return true;
}
-void FileCollector::addFile(const Twine &file) {
- std::lock_guard<std::mutex> lock(Mutex);
- std::string FileStr = file.str();
- if (markAsSeen(FileStr))
- addFileImpl(FileStr);
-}
+void FileCollector::addFile(const Twine &file) { addFileImpl(file.str()); }
void FileCollector::addDirectory(const Twine &dir) {
assert(sys::fs::is_directory(dir));
std::error_code EC;
sys::fs::recursive_directory_iterator Iter(dir, EC);
sys::fs::recursive_directory_iterator End;
- addFile(dir); // Add the directory in case it's empty.
+ addFileImpl(dir.str()); // Add the directory in case it's empty.
for (; Iter != End && !EC; Iter.increment(EC)) {
if (sys::fs::is_regular_file(Iter->path()))
- addFile(Iter->path());
+ addFileImpl(Iter->path());
}
}
void FileCollector::addFileImpl(StringRef SrcPath) {
+ std::lock_guard<std::mutex> lock(Mutex);
+ if (!markAsSeen(SrcPath))
+ return;
+
// We need an absolute src path to append to the root.
SmallString<256> AbsoluteSrc = SrcPath;
sys::fs::make_absolute(AbsoluteSrc);
Index: llvm/include/llvm/Support/FileCollector.h
===================================================================
--- llvm/include/llvm/Support/FileCollector.h
+++ llvm/include/llvm/Support/FileCollector.h
@@ -45,7 +45,7 @@
createCollectorVFS(IntrusiveRefCntPtr<vfs::FileSystem> BaseFS,
std::shared_ptr<FileCollector> Collector);
-private:
+protected:
void addFileImpl(StringRef SrcPath);
bool markAsSeen(StringRef Path) {
@@ -60,7 +60,6 @@
VFSWriter.addFileMapping(VirtualPath, RealPath);
}
-protected:
/// Synchronizes adding files.
std::mutex Mutex;
Index: lldb/test/Shell/Reproducer/TestDSYM.test
===================================================================
--- /dev/null
+++ lldb/test/Shell/Reproducer/TestDSYM.test
@@ -0,0 +1,11 @@
+# REQUIRES: system-darwin
+# Ensure that the reproducers captures the whole dSYM bundle.
+
+# RUN: rm -rf %t.repro
+# RUN: %clang_host %S/Inputs/simple.c -g -o %t.out
+# RUN: touch %t.out.dSYM/foo.bar
+
+# RUN: %lldb -x -b --capture --capture-path %t.repro %t.out -o 'b main' -o 'run' -o 'reproducer generate'
+
+# RUN: %lldb -b -o 'reproducer dump -p files -f %t.repro' | FileCheck %s --check-prefix FILES
+# FILES: foo.bar
Index: lldb/source/Utility/FileCollector.cpp
===================================================================
--- /dev/null
+++ lldb/source/Utility/FileCollector.cpp
@@ -0,0 +1,43 @@
+//===-- FileCollector.cpp ---------------------------------------*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "lldb/Utility/FileCollector.h"
+#include "llvm/ADT/SmallString.h"
+#include "llvm/Support/FileSystem.h"
+#include "llvm/Support/Path.h"
+#include "llvm/Support/Process.h"
+
+using namespace lldb_private;
+
+void FileCollector::addFile(const llvm::Twine &file) {
+ // Add dSYM bundle if applicable.
+ if (addDSYM(file))
+ return;
+
+ // Add the file.
+ addFileImpl(file.str());
+}
+
+bool FileCollector::addDSYM(const llvm::Twine &file) {
+ auto begin = llvm::sys::path::begin(file.str());
+ auto end = llvm::sys::path::end(file.str());
+ llvm::SmallString<128> bundle;
+ for (auto it = begin; it != end; ++it) {
+ if (llvm::sys::path::extension(*it).lower() == ".dsym") {
+ llvm::sys::path::append(bundle, begin, ++it);
+ break;
+ }
+ }
+
+ // If bundle is empty the path is not a dSYM.
+ if (bundle.empty())
+ return false;
+
+ llvm::FileCollector::addDirectory(bundle.str());
+ return true;
+}
Index: lldb/source/Utility/CMakeLists.txt
===================================================================
--- lldb/source/Utility/CMakeLists.txt
+++ lldb/source/Utility/CMakeLists.txt
@@ -24,6 +24,7 @@
DataExtractor.cpp
Environment.cpp
Event.cpp
+ FileCollector.cpp
FileSpec.cpp
GDBRemote.cpp
IOObject.cpp
Index: lldb/include/lldb/Utility/Reproducer.h
===================================================================
--- lldb/include/lldb/Utility/Reproducer.h
+++ lldb/include/lldb/Utility/Reproducer.h
@@ -9,10 +9,10 @@
#ifndef LLDB_UTILITY_REPRODUCER_H
#define LLDB_UTILITY_REPRODUCER_H
+#include "lldb/Utility/FileCollector.h"
#include "lldb/Utility/FileSpec.h"
#include "llvm/ADT/DenseMap.h"
#include "llvm/Support/Error.h"
-#include "llvm/Support/FileCollector.h"
#include "llvm/Support/YAMLTraits.h"
#include <mutex>
@@ -90,13 +90,11 @@
FileProvider(const FileSpec &directory)
: Provider(directory),
- m_collector(std::make_shared<llvm::FileCollector>(
+ m_collector(std::make_shared<FileCollector>(
directory.CopyByAppendingPathComponent("root").GetPath(),
directory.GetPath())) {}
- std::shared_ptr<llvm::FileCollector> GetFileCollector() {
- return m_collector;
- }
+ std::shared_ptr<FileCollector> GetFileCollector() { return m_collector; }
void Keep() override {
auto mapping = GetRoot().CopyByAppendingPathComponent(Info::file);
@@ -109,7 +107,7 @@
static char ID;
private:
- std::shared_ptr<llvm::FileCollector> m_collector;
+ std::shared_ptr<FileCollector> m_collector;
};
/// Provider for the LLDB version number.
Index: lldb/include/lldb/Utility/FileCollector.h
===================================================================
--- /dev/null
+++ lldb/include/lldb/Utility/FileCollector.h
@@ -0,0 +1,31 @@
+//===-- FileCollector.h -----------------------------------------*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLDD_SUPPORT_FILE_COLLECTOR_H
+#define LLDD_SUPPORT_FILE_COLLECTOR_H
+
+#include "llvm/Support/FileCollector.h"
+
+#include <mutex>
+
+namespace lldb_private {
+
+class FileCollector : public llvm::FileCollector {
+public:
+ FileCollector(std::string Root, std::string OverlayRoot)
+ : llvm::FileCollector(Root, OverlayRoot) {}
+
+ void addFile(const llvm::Twine &file) override;
+
+private:
+ bool addDSYM(const llvm::Twine &file);
+};
+
+} // namespace lldb_private
+
+#endif // LLVM_SUPPORT_FILE_COLLECTOR_H
Index: lldb/include/lldb/Host/FileSystem.h
===================================================================
--- lldb/include/lldb/Host/FileSystem.h
+++ lldb/include/lldb/Host/FileSystem.h
@@ -11,12 +11,12 @@
#include "lldb/Host/File.h"
#include "lldb/Utility/DataBufferLLVM.h"
+#include "lldb/Utility/FileCollector.h"
#include "lldb/Utility/FileSpec.h"
#include "lldb/Utility/Status.h"
#include "llvm/ADT/Optional.h"
#include "llvm/Support/Chrono.h"
-#include "llvm/Support/FileCollector.h"
#include "llvm/Support/VirtualFileSystem.h"
#include "lldb/lldb-types.h"
@@ -34,7 +34,7 @@
FileSystem()
: m_fs(llvm::vfs::getRealFileSystem()), m_collector(nullptr),
m_mapped(false) {}
- FileSystem(std::shared_ptr<llvm::FileCollector> collector)
+ FileSystem(std::shared_ptr<FileCollector> collector)
: m_fs(llvm::vfs::getRealFileSystem()), m_collector(collector),
m_mapped(false) {}
FileSystem(llvm::IntrusiveRefCntPtr<llvm::vfs::FileSystem> fs,
@@ -47,7 +47,7 @@
static FileSystem &Instance();
static void Initialize();
- static void Initialize(std::shared_ptr<llvm::FileCollector> collector);
+ static void Initialize(std::shared_ptr<FileCollector> collector);
static llvm::Error Initialize(const FileSpec &mapping);
static void Initialize(llvm::IntrusiveRefCntPtr<llvm::vfs::FileSystem> fs);
static void Terminate();
@@ -190,7 +190,7 @@
void AddFile(const llvm::Twine &file);
static llvm::Optional<FileSystem> &InstanceImpl();
llvm::IntrusiveRefCntPtr<llvm::vfs::FileSystem> m_fs;
- std::shared_ptr<llvm::FileCollector> m_collector;
+ std::shared_ptr<FileCollector> m_collector;
bool m_mapped;
};
} // namespace lldb_private
_______________________________________________
lldb-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits