1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-07-26 19:17:35 +00:00

LibSymbolication: Look for libraries under /usr/local/lib

While trying to investigate a problem with the ssl module in the python
port I found that the SystemMonitor Stack tab for a process wouldn't
show the symbols for the libssl and libcrypto shared libraries that are
installed under /usr/local/lib. The main reason for this is that
LibSymbolication didn't look for libraries under /usr/local/lib.

This commit adds support for looking for libraries under /usr/local/lib.
Absolute paths are still respected, and lookup gives precedence to
/usr/lib, just like dynamic linker does.
This commit is contained in:
Rodrigo Tobar 2021-09-27 23:54:53 +08:00 committed by Andreas Kling
parent f4ebcf4867
commit 12e18e44ae

View file

@ -4,10 +4,12 @@
* SPDX-License-Identifier: BSD-2-Clause * SPDX-License-Identifier: BSD-2-Clause
*/ */
#include <AK/Array.h>
#include <AK/Checked.h> #include <AK/Checked.h>
#include <AK/JsonArray.h> #include <AK/JsonArray.h>
#include <AK/JsonObject.h> #include <AK/JsonObject.h>
#include <AK/JsonValue.h> #include <AK/JsonValue.h>
#include <AK/LexicalPath.h>
#include <AK/MappedFile.h> #include <AK/MappedFile.h>
#include <LibCore/File.h> #include <LibCore/File.h>
#include <LibDebug/DebugInfo.h> #include <LibDebug/DebugInfo.h>
@ -61,24 +63,41 @@ Optional<FlatPtr> kernel_base()
Optional<Symbol> symbolicate(String const& path, FlatPtr address) Optional<Symbol> symbolicate(String const& path, FlatPtr address)
{ {
if (!s_cache.contains(path)) { String full_path = path;
auto mapped_file = MappedFile::map(path); if (!path.starts_with('/')) {
if (mapped_file.is_error()) { Array<StringView, 2> search_paths { "/usr/lib"sv, "/usr/local/lib"sv };
dbgln("Failed to map {}: {}", path, mapped_file.error().string()); bool found = false;
for (auto& search_path : search_paths) {
full_path = LexicalPath::join(search_path, path).string();
if (Core::File::exists(full_path)) {
found = true;
break;
}
}
if (!found) {
dbgln("Failed to find candidate for {}", path);
s_cache.set(path, {}); s_cache.set(path, {});
return {}; return {};
} }
}
if (!s_cache.contains(full_path)) {
auto mapped_file = MappedFile::map(full_path);
if (mapped_file.is_error()) {
dbgln("Failed to map {}: {}", full_path, mapped_file.error().string());
s_cache.set(full_path, {});
return {};
}
auto elf = make<ELF::Image>(mapped_file.value()->bytes()); auto elf = make<ELF::Image>(mapped_file.value()->bytes());
if (!elf->is_valid()) { if (!elf->is_valid()) {
dbgln("ELF not valid: {}", path); dbgln("ELF not valid: {}", full_path);
s_cache.set(path, {}); s_cache.set(full_path, {});
return {}; return {};
} }
auto cached_elf = make<CachedELF>(mapped_file.release_value(), make<Debug::DebugInfo>(*elf), move(elf)); auto cached_elf = make<CachedELF>(mapped_file.release_value(), make<Debug::DebugInfo>(*elf), move(elf));
s_cache.set(path, move(cached_elf)); s_cache.set(full_path, move(cached_elf));
} }
auto it = s_cache.find(path); auto it = s_cache.find(full_path);
VERIFY(it != s_cache.end()); VERIFY(it != s_cache.end());
auto& cached_elf = it->value; auto& cached_elf = it->value;
@ -172,8 +191,6 @@ Vector<Symbol> symbolicate_thread(pid_t pid, pid_t tid)
} else if (name.ends_with(": .text") || name.ends_with(": .rodata")) { } else if (name.ends_with(": .text") || name.ends_with(": .rodata")) {
auto parts = name.split_view(':'); auto parts = name.split_view(':');
path = parts[0]; path = parts[0];
if (!path.starts_with('/'))
path = String::formatted("/usr/lib/{}", path);
} else { } else {
continue; continue;
} }