From 5171e87a51615570ca6300ae1e6ee8b7bb27d971 Mon Sep 17 00:00:00 2001 From: Jeremy <51220084+jeremy-rifkin@users.noreply.github.com> Date: Sat, 25 May 2024 13:38:06 -0500 Subject: [PATCH] Refactor logic in the libdwarf resolver's resolve_frames, pull out trace flattening --- src/symbols/symbols_with_libdwarf.cpp | 104 ++++++++++++++------------ 1 file changed, 56 insertions(+), 48 deletions(-) diff --git a/src/symbols/symbols_with_libdwarf.cpp b/src/symbols/symbols_with_libdwarf.cpp index 7659a52..43db5ee 100644 --- a/src/symbols/symbols_with_libdwarf.cpp +++ b/src/symbols/symbols_with_libdwarf.cpp @@ -1177,54 +1177,8 @@ namespace libdwarf { } } - CPPTRACE_FORCE_NO_INLINE_FOR_PROFILING - std::vector resolve_frames(const std::vector& frames) { - std::vector trace(frames.size(), {null_frame, {}}); - // Locking around all libdwarf interaction per https://github.com/davea42/libdwarf-code/discussions/184 - // And also locking for interactions with get_resolver - static std::mutex mutex; - const std::lock_guard lock(mutex); - for(const auto& group : collate_frames(frames, trace)) { - try { - const auto& object_name = group.first; - auto resolver = get_resolver(object_name); - for(const auto& entry : group.second) { - const auto& dlframe = entry.first.get(); - auto& frame = entry.second.get(); - try { - frame = resolver->resolve_frame(dlframe); - } catch(...) { - frame.frame.raw_address = dlframe.raw_address; - frame.frame.object_address = dlframe.object_address; - frame.frame.filename = dlframe.object_path; - if(!should_absorb_trace_exceptions()) { - throw; - } - } - } - } catch(...) { // NOSONAR - if(!should_absorb_trace_exceptions()) { - throw; - } - for(const auto& entry : group.second) { - const auto& dlframe = entry.first.get(); - auto& frame = entry.second.get(); - frame = { - { - dlframe.raw_address, - dlframe.object_address, - nullable::null(), - nullable::null(), - dlframe.object_path, - "", - false - }, - {} - }; - } - } - } - // flatten trace with inlines + // flatten trace with inlines + std::vector flatten_inlines(const std::vector& trace) { std::vector final_trace; for(const auto& entry : trace) { // most recent call first @@ -1257,6 +1211,60 @@ namespace libdwarf { } return final_trace; } + + CPPTRACE_FORCE_NO_INLINE_FOR_PROFILING + std::vector resolve_frames(const std::vector& frames) { + std::vector trace(frames.size(), {null_frame, {}}); + // Locking around all libdwarf interaction per https://github.com/davea42/libdwarf-code/discussions/184 + // And also locking for interactions with get_resolver + static std::mutex mutex; + const std::lock_guard lock(mutex); + for(const auto& group : collate_frames(frames, trace)) { + try { + const auto& object_name = group.first; + auto resolver = get_resolver(object_name); + for(const auto& entry : group.second) { + const auto& dlframe = entry.first.get(); + auto& frame = entry.second.get(); + try { + frame = resolver->resolve_frame(dlframe); + } catch(...) { + frame.frame.raw_address = dlframe.raw_address; + frame.frame.object_address = dlframe.object_address; + frame.frame.filename = dlframe.object_path; + if(!should_absorb_trace_exceptions()) { + throw; + } + } + } + } catch(...) { // NOSONAR + if(!should_absorb_trace_exceptions()) { + throw; + } + } + } + // fill in basic info for any frames where there were resolution issues + for(std::size_t i = 0; i < frames.size(); i++) { + const auto& dlframe = frames[i]; + auto& frame = trace[i]; + if(frame.frame == null_frame) { + frame = { + { + dlframe.raw_address, + dlframe.object_address, + nullable::null(), + nullable::null(), + dlframe.object_path, + "", + false + }, + {} + }; + } + } + // flatten and finish + return flatten_inlines(trace); + } } } }