kwk updated this revision to Diff 248746.
kwk added a comment.

- Simplified return type of getBuildIDFromModule
- fixed typo


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D75750/new/

https://reviews.llvm.org/D75750

Files:
  lldb/cmake/modules/FindDebuginfod.cmake
  lldb/cmake/modules/LLDBConfig.cmake
  lldb/include/lldb/Host/Config.h.cmake
  lldb/include/lldb/Host/DebugInfoD.h
  lldb/packages/Python/lldbsuite/test/lldbtest.py
  lldb/source/Core/SourceManager.cpp
  lldb/source/Host/CMakeLists.txt
  lldb/source/Host/common/DebugInfoD.cpp

Index: lldb/source/Host/common/DebugInfoD.cpp
===================================================================
--- /dev/null
+++ lldb/source/Host/common/DebugInfoD.cpp
@@ -0,0 +1,120 @@
+//===-- DebugInfoD.cpp ----------------------------------------------------===//
+//
+// 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/Core/Module.h"
+#include "lldb/Host/Config.h"
+#include "lldb/Symbol/ObjectFile.h"
+#include "llvm/ADT/StringRef.h"
+#include "llvm/Support/Error.h"
+#include "lldb/Host/DebugInfoD.h"
+
+#if LLDB_ENABLE_DEBUGINFOD
+#include "elfutils/debuginfod.h"
+#endif
+
+namespace lldb_private {
+
+namespace debuginfod {
+
+using namespace lldb;
+using namespace lldb_private;
+
+#if !LLDB_ENABLE_DEBUGINFOD
+bool isAvailable() { return false; }
+
+UUID getBuildIDFromModule(const ModuleSP &module) {
+  llvm_unreachable("debuginfod::getBuildIDFromModule is unavailable");
+};
+
+llvm::Error findSource(UUID buildID, const std::string &path,
+                       std::string &cache_path, sys::TimePoint<> &mod_time) {
+  llvm_unreachable("debuginfod::findSource is unavailable");
+}
+
+#else // LLDB_ENABLE_DEBUGINFOD
+
+bool isAvailable() { return true; }
+
+UUID getBuildIDFromModule(const ModuleSP &module) {
+  UUID buildID;
+
+  if (!module)
+    return buildID;
+
+  const FileSpec &moduleFileSpec = module->GetFileSpec();
+  ModuleSpecList specList;
+  size_t nSpecs =
+      ObjectFile::GetModuleSpecifications(moduleFileSpec, 0, 0, specList);
+
+  for (size_t i = 0; i < nSpecs; i++) {
+    ModuleSpec spec;
+    if (!specList.GetModuleSpecAtIndex(i, spec))
+      continue;
+
+    const UUID &uuid = spec.GetUUID();
+    if (!uuid.IsValid())
+      continue;
+
+    buildID = uuid;
+    break;
+  }
+  return buildID;
+}
+
+llvm::Error findSource(UUID buildID, const std::string &path,
+                       std::string &result_path) {
+  if (!buildID.IsValid())
+    return llvm::createStringError(llvm::inconvertibleErrorCode(),
+                                   "invalid build ID: %s",
+                                   buildID.GetAsString("").c_str());
+
+  debuginfod_client *client = debuginfod_begin();
+
+  if (!client)
+    return llvm::createStringError(
+        llvm::inconvertibleErrorCode(),
+        "failed to create debuginfod connection handle: %s", strerror(errno));
+
+  // debuginfod_set_progressfn(client, [](debuginfod_client *client, long a,
+  //                                 long b) -> int {
+  //   fprintf(stderr, "KWK === a: %ld b : %ld \n", a, b);
+  //   return 0; // continue
+  // });
+
+  char *cache_path = nullptr;
+  int rc = debuginfod_find_source(client, buildID.GetBytes().data(),
+                                  buildID.GetBytes().size(), path.c_str(),
+                                  &cache_path);
+
+  if (rc < 0)
+    return llvm::createStringError(llvm::inconvertibleErrorCode(),
+                                   "debuginfod_find_source query failed: %s",
+                                   strerror(-rc));
+
+  if (cache_path) {
+    result_path = std::string(cache_path);
+    free(cache_path);
+  }
+
+  llvm::Error err = llvm::Error::success();
+  if (close(rc) < 0) {
+    err = llvm::createStringError(
+        llvm::inconvertibleErrorCode(),
+        "failed to close result of call to debuginfo_find_source: %s",
+        strerror(errno));
+  }
+
+  debuginfod_end(client);
+
+  return err;
+}
+
+#endif // LLDB_ENABLE_DEBUGINFOD
+
+} // end of namespace debuginfod
+} // namespace lldb_private
Index: lldb/source/Host/CMakeLists.txt
===================================================================
--- lldb/source/Host/CMakeLists.txt
+++ lldb/source/Host/CMakeLists.txt
@@ -30,6 +30,7 @@
   common/HostThread.cpp
   common/LockFileBase.cpp
   common/LZMA.cpp
+  common/DebugInfoD.cpp
   common/MainLoop.cpp
   common/MonitoringProcessLauncher.cpp
   common/NativeProcessProtocol.cpp
@@ -161,6 +162,9 @@
 if (LLDB_ENABLE_LZMA)
   list(APPEND EXTRA_LIBS ${LIBLZMA_LIBRARIES})
 endif()
+if (LLDB_ENABLE_DEBUGINFOD)
+  list(APPEND EXTRA_LIBS ${Debuginfod_LIBRARIES})
+endif()
 if (WIN32)
   list(APPEND LLDB_SYSTEM_LIBS psapi)
 endif ()
Index: lldb/source/Core/SourceManager.cpp
===================================================================
--- lldb/source/Core/SourceManager.cpp
+++ lldb/source/Core/SourceManager.cpp
@@ -29,6 +29,7 @@
 #include "lldb/Utility/RegularExpression.h"
 #include "lldb/Utility/Stream.h"
 #include "lldb/lldb-enumerations.h"
+#include "lldb/Host/DebugInfoD.h"
 
 #include "llvm/ADT/Twine.h"
 
@@ -402,7 +403,9 @@
     if (target) {
       m_source_map_mod_id = target->GetSourcePathMap().GetModificationID();
 
-      if (!file_spec.GetDirectory() && file_spec.GetFilename()) {
+      SymbolContext sc;
+      if ((!file_spec.GetDirectory() && file_spec.GetFilename()) ||
+          !FileSystem::Instance().Exists(m_file_spec)) {
         // If this is just a file name, lets see if we can find it in the
         // target:
         bool check_inlines = false;
@@ -416,7 +419,7 @@
         bool got_multiple = false;
         if (num_matches != 0) {
           if (num_matches > 1) {
-            SymbolContext sc;
+            // SymbolContext sc;
             CompileUnit *test_cu = nullptr;
 
             for (unsigned i = 0; i < num_matches; i++) {
@@ -432,11 +435,12 @@
             }
           }
           if (!got_multiple) {
-            SymbolContext sc;
+            // SymbolContext sc;
             sc_list.GetContextAtIndex(0, sc);
             if (sc.comp_unit)
               m_file_spec = sc.comp_unit->GetPrimaryFile();
-            m_mod_time = FileSystem::Instance().GetModificationTime(m_file_spec);
+            m_mod_time =
+                FileSystem::Instance().GetModificationTime(m_file_spec);
           }
         }
       }
@@ -452,6 +456,24 @@
           m_mod_time = FileSystem::Instance().GetModificationTime(m_file_spec);
         }
       }
+
+      // Try finding the file using elfutils' debuginfod
+      if (!FileSystem::Instance().Exists(m_file_spec) &&
+          debuginfod::isAvailable() && sc.module_sp) {
+        UUID buildID = debuginfod::getBuildIDFromModule(sc.module_sp);
+        std::string cache_path;
+        llvm::Error err =
+            debuginfod::findSource(buildID, file_spec.GetCString(), cache_path);
+        if (err) {
+          sc.module_sp->ReportWarning("An error occurred while finding the "
+                                      "source file %s using debuginfod: %s",
+                                      file_spec.GetCString(),
+                                      llvm::toString(std::move(err)).c_str());
+        } else {
+          m_file_spec = FileSpec(cache_path);
+          m_mod_time = FileSystem::Instance().GetModificationTime(cache_path);
+        }
+      }
     }
   }
 
Index: lldb/packages/Python/lldbsuite/test/lldbtest.py
===================================================================
--- lldb/packages/Python/lldbsuite/test/lldbtest.py
+++ lldb/packages/Python/lldbsuite/test/lldbtest.py
@@ -1,7 +1,7 @@
 """
 LLDB module which provides the abstract base class of lldb test case.
 
-The concrete subclass can override lldbtest.TesBase in order to inherit the
+The concrete subclass can override lldbtest.TestBase in order to inherit the
 common behavior for unitest.TestCase.setUp/tearDown implemented in this file.
 
 The subclass should override the attribute mydir in order for the python runtime
Index: lldb/include/lldb/Host/DebugInfoD.h
===================================================================
--- /dev/null
+++ lldb/include/lldb/Host/DebugInfoD.h
@@ -0,0 +1,33 @@
+//===-- DebugInfoD.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 LLDB_HOST_DEBUGINFOD_H
+#define LLDB_HOST_DEBUGINFOD_H
+
+#include "lldb/Utility/UUID.h"
+
+namespace llvm {
+class Error;
+} // End of namespace llvm
+
+namespace lldb_private {
+
+namespace debuginfod {
+	
+bool isAvailable();
+
+UUID getBuildIDFromModule(const lldb::ModuleSP &module);
+
+llvm::Error findSource(UUID buildID, const std::string &path,
+                       std::string &result_path);
+
+} // End of namespace debuginfod
+
+} // End of namespace lldb_private
+
+#endif // LLDB_HOST_DEBUGINFOD_H
Index: lldb/include/lldb/Host/Config.h.cmake
===================================================================
--- lldb/include/lldb/Host/Config.h.cmake
+++ lldb/include/lldb/Host/Config.h.cmake
@@ -36,6 +36,8 @@
 
 #cmakedefine01 LLDB_ENABLE_LZMA
 
+#cmakedefine01 LLDB_ENABLE_DEBUGINFOD
+
 #cmakedefine01 LLDB_ENABLE_CURSES
 
 #cmakedefine01 LLDB_ENABLE_LIBEDIT
Index: lldb/cmake/modules/LLDBConfig.cmake
===================================================================
--- lldb/cmake/modules/LLDBConfig.cmake
+++ lldb/cmake/modules/LLDBConfig.cmake
@@ -58,6 +58,7 @@
 add_optional_dependency(LLDB_ENABLE_LUA "Enable Lua scripting support in LLDB" LuaAndSwig LUAANDSWIG_FOUND)
 add_optional_dependency(LLDB_ENABLE_PYTHON "Enable Python scripting support in LLDB" PythonInterpAndLibs PYTHONINTERPANDLIBS_FOUND)
 add_optional_dependency(LLDB_ENABLE_LIBXML2 "Enable Libxml 2 support in LLDB" LibXml2 LIBXML2_FOUND VERSION 2.8)
+add_optional_dependency(LLDB_ENABLE_DEBUGINFOD "Enable Debuginfod support in LLDB" Debuginfod Debuginfod_FOUND)
 
 option(LLDB_USE_SYSTEM_SIX "Use six.py shipped with system and do not install a copy of it" OFF)
 option(LLDB_USE_ENTITLEMENTS "When codesigning, use entitlements if available" ON)
@@ -233,6 +234,10 @@
   include_directories(${LIBLZMA_INCLUDE_DIRS})
 endif()
 
+if (LLDB_ENABLE_DEBUGINFOD)
+  include_directories(${Debuginfod_INCLUDE_DIRS})
+endif()
+
 if (LLDB_ENABLE_LIBXML2)
   list(APPEND system_libs ${LIBXML2_LIBRARIES})
   include_directories(${LIBXML2_INCLUDE_DIR})
Index: lldb/cmake/modules/FindDebuginfod.cmake
===================================================================
--- /dev/null
+++ lldb/cmake/modules/FindDebuginfod.cmake
@@ -0,0 +1,58 @@
+#.rst:
+# FindDebuginfod
+# -----------
+#
+# Find debuginfod library and headers
+#
+# The module defines the following variables:
+#
+# ::
+#
+#   Debuginfod_FOUND          - true if debuginfod was found
+#   Debuginfod_INCLUDE_DIRS   - include search path
+#   Debuginfod_LIBRARIES      - libraries to link
+#   Debuginfod_VERSION_STRING - version number
+#
+# TODO(kwk): Debuginfod_VERSION_STRING is only set if pkg-config file is
+# available. Trying to see if we can get a MAJOR, MINOR, PATCH define in the
+# debuginfod.h file.
+
+if(Debuginfod_INCLUDE_DIRS AND Debuginfod_LIBRARIES)
+  set(Debuginfod_FOUND TRUE)
+else()
+  # Utilize package config (e.g. /usr/lib64/pkgconfig/libdebuginfod.pc) to fetch
+  # version information. 
+  find_package(PkgConfig QUIET)
+  pkg_check_modules(PC_Debuginfod QUIET libdebuginfod)
+
+  find_path(Debuginfod_INCLUDE_DIRS
+            NAMES
+              elfutils/debuginfod.h
+            HINTS
+              /usr/include
+              ${PC_Debuginfod_INCLUDEDIR}
+              ${PC_Debuginfod_INCLUDE_DIRS}
+              ${CMAKE_INSTALL_FULL_INCLUDEDIR})
+  find_library(Debuginfod_LIBRARIES
+               NAMES
+                 debuginfod
+               HINTS
+                 ${PC_Debuginfod_LIBDIR}
+                 ${PC_Debuginfod_LIBRARY_DIRS}
+                 ${CMAKE_INSTALL_FULL_LIBDIR})
+
+  if(Debuginfod_INCLUDE_DIRS AND EXISTS "${Debuginfod_INCLUDE_DIRS}/debuginfod.h")
+    set(Debuginfod_VERSION_STRING "${PC_Debuginfod_VERSION}")
+  endif()
+
+  include(FindPackageHandleStandardArgs)
+  find_package_handle_standard_args(Debuginfod
+                                    FOUND_VAR
+                                      Debuginfod_FOUND
+                                    REQUIRED_VARS
+                                      Debuginfod_INCLUDE_DIRS
+                                      Debuginfod_LIBRARIES
+                                    VERSION_VAR
+                                      Debuginfod_VERSION_STRING)
+  mark_as_advanced(Debuginfod_INCLUDE_DIRS Debuginfod_LIBRARIES)
+endif()
\ No newline at end of file
_______________________________________________
lldb-commits mailing list
lldb-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits

Reply via email to