~HostInfoBase() {}
public:
- static void Initialize();
+ /// A helper function for determining the liblldb location. It receives a
+ /// FileSpec with the location of file containing _this_ code. It can
+ /// (optionally) replace it with a file spec pointing to a more canonical
+ /// copy.
+ using SharedLibraryDirectoryHelper = void(FileSpec &this_file);
+
+ static void Initialize(SharedLibraryDirectoryHelper *helper = nullptr);
static void Terminate();
/// Gets the host target triple.
~HostInfoLinux();
public:
- static void Initialize();
+ static void Initialize(SharedLibraryDirectoryHelper *helper = nullptr);
static llvm::VersionTuple GetOSVersion();
static bool GetOSBuildString(std::string &s);
~HostInfoWindows();
public:
- static void Initialize();
+ static void Initialize(SharedLibraryDirectoryHelper *helper = nullptr);
static void Terminate();
static size_t GetPageSize();
#define LLDB_INITIALIZATION_SYSTEMINITIALIZERCOMMON_H
#include "SystemInitializer.h"
+#include "lldb/Host/HostInfo.h"
namespace lldb_private {
/// Initializes common lldb functionality.
/// the constructor.
class SystemInitializerCommon : public SystemInitializer {
public:
- SystemInitializerCommon();
+ SystemInitializerCommon(HostInfo::SharedLibraryDirectoryHelper *helper);
~SystemInitializerCommon() override;
llvm::Error Initialize() override;
void Terminate() override;
+
+private:
+ HostInfo::SharedLibraryDirectoryHelper *m_shlib_dir_helper;
};
} // namespace lldb_private
#define LLDB_PLUGIN(p) LLDB_PLUGIN_DECLARE(p)
#include "Plugins/Plugins.def"
+#if LLDB_ENABLE_PYTHON
+#include "Plugins/ScriptInterpreter/Python/ScriptInterpreterPython.h"
+
+constexpr lldb_private::HostInfo::SharedLibraryDirectoryHelper
+ *g_shlib_dir_helper =
+ lldb_private::ScriptInterpreterPython::SharedLibraryDirectoryHelper;
+
+#else
+constexpr lldb_private::HostInfo::SharedLibraryDirectoryHelper
+ *g_shlib_dir_helper = 0;
+#endif
+
using namespace lldb_private;
-SystemInitializerFull::SystemInitializerFull() = default;
+SystemInitializerFull::SystemInitializerFull()
+ : SystemInitializerCommon(g_shlib_dir_helper) {}
SystemInitializerFull::~SystemInitializerFull() = default;
llvm::Error SystemInitializerFull::Initialize() {
llvm::once_flag m_lldb_global_tmp_dir_once;
FileSpec m_lldb_global_tmp_dir;
};
+} // namespace
-HostInfoBaseFields *g_fields = nullptr;
-}
+static HostInfoBaseFields *g_fields = nullptr;
+static HostInfoBase::SharedLibraryDirectoryHelper *g_shlib_dir_helper = nullptr;
-void HostInfoBase::Initialize() { g_fields = new HostInfoBaseFields(); }
+void HostInfoBase::Initialize(SharedLibraryDirectoryHelper *helper) {
+ g_shlib_dir_helper = helper;
+ g_fields = new HostInfoBaseFields();
+}
void HostInfoBase::Terminate() {
+ g_shlib_dir_helper = nullptr;
delete g_fields;
g_fields = nullptr;
}
reinterpret_cast<void *>(
HostInfoBase::ComputeSharedLibraryDirectory)));
- // This is necessary because when running the testsuite the shlib might be a
- // symbolic link inside the Python resource dir.
- FileSystem::Instance().ResolveSymbolicLink(lldb_file_spec, lldb_file_spec);
+ if (g_shlib_dir_helper)
+ g_shlib_dir_helper(lldb_file_spec);
// Remove the filename so that this FileSpec only represents the directory.
file_spec.GetDirectory() = lldb_file_spec.GetDirectory();
HostInfoLinuxFields *g_fields = nullptr;
}
-void HostInfoLinux::Initialize() {
- HostInfoPosix::Initialize();
+void HostInfoLinux::Initialize(SharedLibraryDirectoryHelper *helper) {
+ HostInfoPosix::Initialize(helper);
g_fields = new HostInfoLinuxFields();
}
FileSpec HostInfoWindows::m_program_filespec;
-void HostInfoWindows::Initialize() {
+void HostInfoWindows::Initialize(SharedLibraryDirectoryHelper *helper) {
::CoInitializeEx(nullptr, COINIT_MULTITHREADED);
- HostInfoBase::Initialize();
+ HostInfoBase::Initialize(helper);
}
void HostInfoWindows::Terminate() {
#include "Plugins/Process/gdb-remote/ProcessGDBRemoteLog.h"
#include "lldb/Host/FileSystem.h"
#include "lldb/Host/Host.h"
-#include "lldb/Host/HostInfo.h"
#include "lldb/Host/Socket.h"
#include "lldb/Utility/Log.h"
#include "lldb/Utility/ReproducerProvider.h"
using namespace lldb_private;
using namespace lldb_private::repro;
-SystemInitializerCommon::SystemInitializerCommon() {}
+SystemInitializerCommon::SystemInitializerCommon(
+ HostInfo::SharedLibraryDirectoryHelper *helper)
+ : m_shlib_dir_helper(helper) {}
SystemInitializerCommon::~SystemInitializerCommon() {}
return e;
Log::Initialize();
- HostInfo::Initialize();
+ HostInfo::Initialize(m_shlib_dir_helper);
llvm::Error error = Socket::Initialize();
if (error)
return g_spec;
}
+void ScriptInterpreterPython::SharedLibraryDirectoryHelper(
+ FileSpec &this_file) {
+ // When we're loaded from python, this_file will point to the file inside the
+ // python package directory. Replace it with the one in the lib directory.
+#ifdef _WIN32
+ // On windows, we need to manually back out of the python tree, and go into
+ // the bin directory. This is pretty much the inverse of what ComputePythonDir
+ // does.
+ if (this_file.GetFileNameExtension() == ConstString(".pyd")) {
+ this_file.RemoveLastPathComponent(); // _lldb.pyd or _lldb_d.pyd
+ this_file.RemoveLastPathComponent(); // lldb
+ for (auto it = llvm::sys::path::begin(LLDB_PYTHON_RELATIVE_LIBDIR),
+ end = llvm::sys::path::end(LLDB_PYTHON_RELATIVE_LIBDIR);
+ it != end; ++it)
+ this_file.RemoveLastPathComponent();
+ this_file.AppendPathComponent("bin");
+ this_file.AppendPathComponent("liblldb.dll");
+ }
+#else
+ // The python file is a symlink, so we can find the real library by resolving
+ // it. We can do this unconditionally.
+ FileSystem::Instance().ResolveSymbolicLink(this_file, this_file);
+#endif
+}
+
lldb_private::ConstString ScriptInterpreterPython::GetPluginNameStatic() {
static ConstString g_name("script-python");
return g_name;
static lldb_private::ConstString GetPluginNameStatic();
static const char *GetPluginDescriptionStatic();
static FileSpec GetPythonDir();
+ static void SharedLibraryDirectoryHelper(FileSpec &this_file);
protected:
static void ComputePythonDirForApple(llvm::SmallVectorImpl<char> &path);
from lldbsuite.test.decorators import *
from lldbsuite.test.lldbtest import *
from lldbsuite.test import lldbutil
+from lldbsuite.test import lldbplatformutil
class TestPaths(TestBase):
for path_type in dir_path_types:
f = lldb.SBHostOS.GetLLDBPath(path_type)
# No directory path types should have the filename set
- self.assertTrue(f.GetFilename() is None)
+ self.assertIsNone(f.GetFilename())
+
+ shlib_dir = lldb.SBHostOS.GetLLDBPath(lldb.ePathTypeLLDBShlibDir).GetDirectory()
+ if lldbplatformutil.getHostPlatform() == 'windows':
+ filenames = ['liblldb.dll']
+ elif lldbplatformutil.getHostPlatform() == 'darwin':
+ filenames = ['LLDB', 'liblldb.dylib']
+ else:
+ filenames = ['liblldb.so']
+ self.assertTrue(any([os.path.exists(os.path.join(shlib_dir, f)) for f in
+ filenames]), "shlib_dir = " + shlib_dir)
+
@no_debug_info_test
def test_directory_doesnt_end_with_slash(self):
class SystemInitializerLLGS : public lldb_private::SystemInitializerCommon {
public:
+ SystemInitializerLLGS() : SystemInitializerCommon(nullptr) {}
+
llvm::Error Initialize() override;
void Terminate() override;
};
using namespace lldb_private;
-SystemInitializerTest::SystemInitializerTest() = default;
+SystemInitializerTest::SystemInitializerTest()
+ : SystemInitializerCommon(nullptr) {}
SystemInitializerTest::~SystemInitializerTest() = default;
llvm::Error SystemInitializerTest::Initialize() {