[Lldb-commits] [lldb] [lldb] Start using formatv() in RegisterContextUnwind (PR #191576)

via lldb-commits lldb-commits at lists.llvm.org
Fri Apr 10 17:15:11 PDT 2026


llvmbot wrote:


<!--LLVM PR SUMMARY COMMENT-->

@llvm/pr-subscribers-lldb

Author: Sergei Barannikov (s-barannikov)

<details>
<summary>Changes</summary>

This introduces two macros that do the same `UnwindLogMsg()`/`UnwindLogMsgVerbose()` functions, but allow using `formatv()`-style formatting. In addition to the benefits that the `formatv()` function provides, this allows the `lldb log enable -F unwind` to print the correct methods names from which the messages originate (previously, it printed the name of one of those two helper methods).

I didn't replace all function calls with macros because there are too many of them for one PR. This only replaces calls whose format string contains no specifiers or only one '%s'.


---

Patch is 29.94 KiB, truncated to 20.00 KiB below, full version: https://github.com/llvm/llvm-project/pull/191576.diff


1 Files Affected:

- (modified) lldb/source/Target/RegisterContextUnwind.cpp (+129-105) 


``````````diff
diff --git a/lldb/source/Target/RegisterContextUnwind.cpp b/lldb/source/Target/RegisterContextUnwind.cpp
index 3db2c38fed0cb..adc3ee054a976 100644
--- a/lldb/source/Target/RegisterContextUnwind.cpp
+++ b/lldb/source/Target/RegisterContextUnwind.cpp
@@ -37,6 +37,7 @@
 #include "lldb/Utility/RegisterValue.h"
 #include "lldb/Utility/VASPrintf.h"
 #include "lldb/lldb-private.h"
+#include "llvm/Support/FormatAdapters.h"
 
 #include <cassert>
 #include <memory>
@@ -60,6 +61,16 @@ static bool CallFrameAddressIsValid(ABISP abi_sp, lldb::addr_t cfa) {
   return cfa != 0 && cfa != 1;
 }
 
+#define UNWIND_LOG(log, ...)                                                   \
+  LLDB_LOG(log, "{0}th{1}/fr{2} {3}",                                          \
+           llvm::indent(std::min(m_frame_number, 100U)),                       \
+           m_thread.GetIndexID(), m_frame_number, llvm::formatv(__VA_ARGS__))
+
+#define UNWIND_LOG_VERBOSE(log, ...)                                           \
+  LLDB_LOG_VERBOSE(                                                            \
+      log, "{0}th{1}/fr{2} {3}", llvm::indent(std::min(m_frame_number, 100U)), \
+      m_thread.GetIndexID(), m_frame_number, llvm::formatv(__VA_ARGS__))
+
 RegisterContextUnwind::RegisterContextUnwind(Thread &thread,
                                              const SharedPtr &next_frame,
                                              SymbolContext &sym_ctx,
@@ -127,7 +138,7 @@ void RegisterContextUnwind::InitializeZerothFrame() {
 
   if (reg_ctx_sp.get() == nullptr) {
     m_frame_type = eNotAValidFrame;
-    UnwindLogMsg("frame does not have a register context");
+    UNWIND_LOG(log, "frame does not have a register context");
     return;
   }
 
@@ -135,7 +146,7 @@ void RegisterContextUnwind::InitializeZerothFrame() {
 
   if (current_pc == LLDB_INVALID_ADDRESS) {
     m_frame_type = eNotAValidFrame;
-    UnwindLogMsg("frame does not have a pc");
+    UNWIND_LOG(log, "frame does not have a pc");
     return;
   }
 
@@ -153,7 +164,7 @@ void RegisterContextUnwind::InitializeZerothFrame() {
       LanguageRuntime::GetRuntimeUnwindPlan(m_thread, this,
                                             m_behaves_like_zeroth_frame);
   if (lang_runtime_plan_sp.get()) {
-    UnwindLogMsg("This is an async frame");
+    UNWIND_LOG(log, "This is an async frame");
   }
 
   // Initialize m_current_pc, an Address object, based on current_pc, an
@@ -165,7 +176,7 @@ void RegisterContextUnwind::InitializeZerothFrame() {
   // hope we can unwind past this frame.
   ModuleSP pc_module_sp(m_current_pc.GetModule());
   if (!m_current_pc.IsValid() || !pc_module_sp) {
-    UnwindLogMsg("using architectural default unwind method");
+    UNWIND_LOG(log, "using architectural default unwind method");
   }
 
   m_sym_ctx_valid = m_current_pc.ResolveFunctionScope(m_sym_ctx);
@@ -224,14 +235,14 @@ void RegisterContextUnwind::InitializeZerothFrame() {
     row_register_kind = lang_runtime_plan_sp->GetRegisterKind();
     if (!ReadFrameAddress(row_register_kind, active_row->GetCFAValue(),
                           m_cfa)) {
-      UnwindLogMsg("Cannot set cfa");
+      UNWIND_LOG(log, "Cannot set cfa");
     } else {
       m_full_unwind_plan_sp = lang_runtime_plan_sp;
       if (log) {
         StreamString active_row_strm;
         active_row->Dump(active_row_strm, lang_runtime_plan_sp.get(), &m_thread,
                          m_start_pc.GetLoadAddress(exe_ctx.GetTargetPtr()));
-        UnwindLogMsg("async active row: %s", active_row_strm.GetData());
+        UNWIND_LOG(log, "async active row: {0}", active_row_strm.GetString());
       }
       UnwindLogMsg("m_cfa = 0x%" PRIx64 " m_afa = 0x%" PRIx64, m_cfa, m_afa);
       UnwindLogMsg(
@@ -254,12 +265,12 @@ void RegisterContextUnwind::InitializeZerothFrame() {
       StreamString active_row_strm;
       active_row->Dump(active_row_strm, m_full_unwind_plan_sp.get(), &m_thread,
                        m_start_pc.GetLoadAddress(exe_ctx.GetTargetPtr()));
-      UnwindLogMsg("%s", active_row_strm.GetData());
+      UNWIND_LOG(log, "{0}", active_row_strm.GetString());
     }
   }
 
   if (!active_row) {
-    UnwindLogMsg("could not find an unwindplan row for this frame's pc");
+    UNWIND_LOG(log, "could not find an unwindplan row for this frame's pc");
     m_frame_type = eNotAValidFrame;
     return;
   }
@@ -287,7 +298,7 @@ void RegisterContextUnwind::InitializeZerothFrame() {
         cfa_status = true;
     }
     if (!cfa_status) {
-      UnwindLogMsg("could not read CFA value for first frame.");
+      UNWIND_LOG(log, "could not read CFA value for first frame.");
       m_frame_type = eNotAValidFrame;
       return;
     }
@@ -295,8 +306,8 @@ void RegisterContextUnwind::InitializeZerothFrame() {
     ReadFrameAddress(row_register_kind, active_row->GetAFAValue(), m_afa);
 
   if (m_cfa == LLDB_INVALID_ADDRESS && m_afa == LLDB_INVALID_ADDRESS) {
-    UnwindLogMsg(
-        "could not read CFA or AFA values for first frame, not valid.");
+    UNWIND_LOG(log,
+               "could not read CFA or AFA values for first frame, not valid.");
     m_frame_type = eNotAValidFrame;
     return;
   }
@@ -319,20 +330,20 @@ void RegisterContextUnwind::InitializeNonZerothFrame() {
   Log *log = GetLog(LLDBLog::Unwind);
   if (IsFrameZero()) {
     m_frame_type = eNotAValidFrame;
-    UnwindLogMsg("non-zeroth frame tests positive for IsFrameZero -- that "
-                 "shouldn't happen.");
+    UNWIND_LOG(log, "non-zeroth frame tests positive for IsFrameZero -- that "
+                    "shouldn't happen.");
     return;
   }
 
   if (!GetNextFrame().get() || !GetNextFrame()->IsValid()) {
     m_frame_type = eNotAValidFrame;
-    UnwindLogMsg("Could not get next frame, marking this frame as invalid.");
+    UNWIND_LOG(log, "Could not get next frame, marking this frame as invalid.");
     return;
   }
   if (!m_thread.GetRegisterContext()) {
     m_frame_type = eNotAValidFrame;
-    UnwindLogMsg("Could not get register context for this thread, marking this "
-                 "frame as invalid.");
+    UNWIND_LOG(log, "Could not get register context for this thread, marking "
+                    "this frame as invalid.");
     return;
   }
 
@@ -350,12 +361,12 @@ void RegisterContextUnwind::InitializeNonZerothFrame() {
       LanguageRuntime::GetRuntimeUnwindPlan(m_thread, this,
                                             m_behaves_like_zeroth_frame);
   if (lang_runtime_plan_sp.get()) {
-    UnwindLogMsg("This is an async frame");
+    UNWIND_LOG(log, "This is an async frame");
   }
 
   addr_t pc;
   if (!ReadGPRValue(eRegisterKindGeneric, LLDB_REGNUM_GENERIC_PC, pc)) {
-    UnwindLogMsg("could not get pc value");
+    UNWIND_LOG(log, "could not get pc value");
     m_frame_type = eNotAValidFrame;
     return;
   }
@@ -385,7 +396,7 @@ void RegisterContextUnwind::InitializeNonZerothFrame() {
   if (pc == 0 || pc == 0x1) {
     if (!above_trap_handler) {
       m_frame_type = eNotAValidFrame;
-      UnwindLogMsg("this frame has a pc of 0x0");
+      UNWIND_LOG(log, "this frame has a pc of 0x0");
       return;
     }
   }
@@ -402,7 +413,7 @@ void RegisterContextUnwind::InitializeNonZerothFrame() {
   ModuleSP pc_module_sp(m_current_pc.GetModule());
   if ((!m_current_pc.IsValid() || !pc_module_sp) &&
       above_trap_handler == false) {
-    UnwindLogMsg("using architectural default unwind method");
+    UNWIND_LOG(log, "using architectural default unwind method");
 
     // Test the pc value to see if we know it's in an unmapped/non-executable
     // region of memory.
@@ -425,8 +436,8 @@ void RegisterContextUnwind::InitializeNonZerothFrame() {
         // anywhere other than the second frame, a non-executable pc means
         // we're off in the weeds -- stop now.
         m_frame_type = eNotAValidFrame;
-        UnwindLogMsg("pc is in a non-executable section of memory and this "
-                     "isn't the 2nd frame in the stack walk.");
+        UNWIND_LOG(log, "pc is in a non-executable section of memory and this "
+                        "isn't the 2nd frame in the stack walk.");
         return;
       }
     }
@@ -445,7 +456,7 @@ void RegisterContextUnwind::InitializeNonZerothFrame() {
       if (const UnwindPlan::Row *row =
               m_full_unwind_plan_sp->GetRowForFunctionOffset(0)) {
         if (!ReadFrameAddress(row_register_kind, row->GetCFAValue(), m_cfa)) {
-          UnwindLogMsg("failed to get cfa value");
+          UNWIND_LOG(log, "failed to get cfa value");
           if (m_frame_type != eSkipFrame) // don't override eSkipFrame
           {
             m_frame_type = eNotAValidFrame;
@@ -457,7 +468,7 @@ void RegisterContextUnwind::InitializeNonZerothFrame() {
 
         // A couple of sanity checks..
         if (!CallFrameAddressIsValid(abi_sp, m_cfa)) {
-          UnwindLogMsg("could not find a valid cfa address");
+          UNWIND_LOG(log, "could not find a valid cfa address");
           m_frame_type = eNotAValidFrame;
           return;
         }
@@ -467,12 +478,12 @@ void RegisterContextUnwind::InitializeNonZerothFrame() {
         if (process->GetLoadAddressPermissions(m_cfa, permissions) &&
             (permissions & ePermissionsReadable) == 0) {
           m_frame_type = eNotAValidFrame;
-          UnwindLogMsg(
-              "the CFA points to a region of memory that is not readable");
+          UNWIND_LOG(
+              log, "the CFA points to a region of memory that is not readable");
           return;
         }
       } else {
-        UnwindLogMsg("could not find a row for function offset zero");
+        UNWIND_LOG(log, "could not find a row for function offset zero");
         m_frame_type = eNotAValidFrame;
         return;
       }
@@ -480,8 +491,8 @@ void RegisterContextUnwind::InitializeNonZerothFrame() {
       if (CheckIfLoopingStack()) {
         TryFallbackUnwindPlan();
         if (CheckIfLoopingStack()) {
-          UnwindLogMsg("same CFA address as next frame, assuming the unwind is "
-                       "looping - stopping");
+          UNWIND_LOG(log, "same CFA address as next frame, assuming the unwind "
+                          "is looping - stopping");
           m_frame_type = eNotAValidFrame;
           return;
         }
@@ -495,8 +506,8 @@ void RegisterContextUnwind::InitializeNonZerothFrame() {
       return;
     }
     m_frame_type = eNotAValidFrame;
-    UnwindLogMsg("could not find any symbol for this pc, or a default unwind "
-                 "plan, to continue unwind.");
+    UNWIND_LOG(log, "could not find any symbol for this pc, or a default "
+                    "unwind plan, to continue unwind.");
     return;
   }
 
@@ -560,8 +571,7 @@ void RegisterContextUnwind::InitializeNonZerothFrame() {
     m_sym_ctx.Clear(false);
     m_sym_ctx_valid = temporary_pc.ResolveFunctionScope(m_sym_ctx);
 
-    UnwindLogMsg("Symbol is now %s",
-                 GetSymbolOrFunctionName(m_sym_ctx).AsCString(""));
+    UNWIND_LOG(log, "Symbol is now {0}", GetSymbolOrFunctionName(m_sym_ctx));
   }
 
   // If we were able to find a symbol/function, set addr_range_ptr to the
@@ -608,14 +618,14 @@ void RegisterContextUnwind::InitializeNonZerothFrame() {
     row_register_kind = lang_runtime_plan_sp->GetRegisterKind();
     if (!ReadFrameAddress(row_register_kind, active_row->GetCFAValue(),
                           m_cfa)) {
-      UnwindLogMsg("Cannot set cfa");
+      UNWIND_LOG(log, "Cannot set cfa");
     } else {
       m_full_unwind_plan_sp = lang_runtime_plan_sp;
       if (log) {
         StreamString active_row_strm;
         active_row->Dump(active_row_strm, lang_runtime_plan_sp.get(), &m_thread,
                          m_start_pc.GetLoadAddress(exe_ctx.GetTargetPtr()));
-        UnwindLogMsg("async active row: %s", active_row_strm.GetData());
+        UNWIND_LOG(log, "async active row: {0}", active_row_strm.GetString());
       }
       UnwindLogMsg("m_cfa = 0x%" PRIx64 " m_afa = 0x%" PRIx64, m_cfa, m_afa);
       UnwindLogMsg(
@@ -645,9 +655,9 @@ void RegisterContextUnwind::InitializeNonZerothFrame() {
       StreamString active_row_strm;
       active_row->Dump(active_row_strm, m_fast_unwind_plan_sp.get(), &m_thread,
                        m_start_pc.GetLoadAddress(exe_ctx.GetTargetPtr()));
-      UnwindLogMsg("Using fast unwind plan '%s'",
-                   m_fast_unwind_plan_sp->GetSourceName().AsCString(""));
-      UnwindLogMsg("active row: %s", active_row_strm.GetData());
+      UNWIND_LOG(log, "Using fast unwind plan '{0}'",
+                 m_fast_unwind_plan_sp->GetSourceName());
+      UNWIND_LOG(log, "active row: {0}", active_row_strm.GetString());
     }
   } else {
     m_full_unwind_plan_sp = GetFullUnwindPlanForFrame();
@@ -661,21 +671,21 @@ void RegisterContextUnwind::InitializeNonZerothFrame() {
         active_row->Dump(active_row_strm, m_full_unwind_plan_sp.get(),
                          &m_thread,
                          m_start_pc.GetLoadAddress(exe_ctx.GetTargetPtr()));
-        UnwindLogMsg("Using full unwind plan '%s'",
-                     m_full_unwind_plan_sp->GetSourceName().AsCString(""));
-        UnwindLogMsg("active row: %s", active_row_strm.GetData());
+        UNWIND_LOG(log, "Using full unwind plan '{0}'",
+                   m_full_unwind_plan_sp->GetSourceName());
+        UNWIND_LOG(log, "active row: {0}", active_row_strm.GetString());
       }
     }
   }
 
   if (!active_row) {
     m_frame_type = eNotAValidFrame;
-    UnwindLogMsg("could not find unwind row for this pc");
+    UNWIND_LOG(log, "could not find unwind row for this pc");
     return;
   }
 
   if (!ReadFrameAddress(row_register_kind, active_row->GetCFAValue(), m_cfa)) {
-    UnwindLogMsg("failed to get cfa");
+    UNWIND_LOG(log, "failed to get cfa");
     m_frame_type = eNotAValidFrame;
     return;
   }
@@ -687,8 +697,8 @@ void RegisterContextUnwind::InitializeNonZerothFrame() {
   if (CheckIfLoopingStack()) {
     TryFallbackUnwindPlan();
     if (CheckIfLoopingStack()) {
-      UnwindLogMsg("same CFA address as next frame, assuming the unwind is "
-                   "looping - stopping");
+      UNWIND_LOG(log, "same CFA address as next frame, assuming the unwind is "
+                      "looping - stopping");
       m_frame_type = eNotAValidFrame;
       return;
     }
@@ -798,6 +808,7 @@ RegisterContextUnwind::GetFastUnwindPlanForFrame() {
 
 std::shared_ptr<const UnwindPlan>
 RegisterContextUnwind::GetFullUnwindPlanForFrame() {
+  Log *log = GetLog(LLDBLog::Unwind);
   std::shared_ptr<const UnwindPlan> arch_default_unwind_plan_sp;
   ExecutionContext exe_ctx(m_thread.shared_from_this());
   Process *process = exe_ctx.GetProcessPtr();
@@ -805,8 +816,8 @@ RegisterContextUnwind::GetFullUnwindPlanForFrame() {
   if (abi) {
     arch_default_unwind_plan_sp = abi->CreateDefaultUnwindPlan();
   } else {
-    UnwindLogMsg(
-        "unable to get architectural default UnwindPlan from ABI plugin");
+    UNWIND_LOG(
+        log, "unable to get architectural default UnwindPlan from ABI plugin");
   }
 
   if (IsFrameZero() || GetNextFrame()->m_frame_type == eTrapHandlerFrame ||
@@ -944,9 +955,10 @@ RegisterContextUnwind::GetFullUnwindPlanForFrame() {
       unwind_plan_sp =
           func_unwinders_sp->GetObjectFileUnwindPlan(process->GetTarget());
     if (unwind_plan_sp && unwind_plan_sp->PlanValidAtAddress(m_current_pc)) {
-      UnwindLogMsgVerbose("frame uses %s for full UnwindPlan because the "
-                          "DynamicLoader suggested we prefer it",
-                          unwind_plan_sp->GetSourceName().GetCString());
+      UNWIND_LOG_VERBOSE(log,
+                         "frame uses {0} for full UnwindPlan because the "
+                         "DynamicLoader suggested we prefer it",
+                         unwind_plan_sp->GetSourceName());
       return unwind_plan_sp;
     }
   }
@@ -981,10 +993,11 @@ RegisterContextUnwind::GetFullUnwindPlanForFrame() {
           m_fallback_unwind_plan_sp = arch_default_unwind_plan_sp;
         }
       }
-      UnwindLogMsgVerbose("frame uses %s for full UnwindPlan because this "
-                          "is the non-call site unwind plan and this is a "
-                          "zeroth frame",
-                          unwind_plan_sp->GetSourceName().GetCString());
+      UNWIND_LOG_VERBOSE(
+          log,
+          "frame uses {0} for full UnwindPlan because this is the non-call "
+          "site unwind plan and this is a zeroth frame",
+          unwind_plan_sp->GetSourceName());
       return unwind_plan_sp;
     }
 
@@ -996,9 +1009,10 @@ RegisterContextUnwind::GetFullUnwindPlanForFrame() {
           func_unwinders_sp->GetUnwindPlanArchitectureDefaultAtFunctionEntry(
               m_thread);
       if (unwind_plan_sp) {
-        UnwindLogMsgVerbose("frame uses %s for full UnwindPlan because we are at "
-                            "the first instruction of a function",
-                            unwind_plan_sp->GetSourceName().GetCString());
+        UNWIND_LOG_VERBOSE(log,
+                           "frame uses {0} for full UnwindPlan because we are "
+                           "at the first instruction of a function",
+                           unwind_plan_sp->GetSourceName());
         return unwind_plan_sp;
       }
     }
@@ -1012,9 +1026,10 @@ RegisterContextUnwind::GetFullUnwindPlanForFrame() {
         process->GetTarget(), m_thread);
   }
   if (IsUnwindPlanValidForCurrentPC(unwind_plan_sp)) {
-    UnwindLogMsgVerbose("frame uses %s for full UnwindPlan because this "
-                        "is the call-site unwind plan",
-                        unwind_plan_sp->GetSourceName().GetCString());
+    UNWIND_LOG_VERBOSE(log,
+                       "frame uses {0} for full UnwindPlan because this is the "
+                       "call-site unwind plan",
+                       unwind_plan_sp->GetSourceName());
     return unwind_plan_sp;
   }
 
@@ -1051,22 +1066,23 @@ RegisterContextUnwind::GetFullUnwindPlanForFrame() {
   }
 
   if (IsUnwindPlanValidForCurrentPC(unwind_plan_sp)) {
-    UnwindLogMsgVerbose("frame uses %s for full UnwindPlan because we "
-                        "failed to find a call-site unwind plan that would work",
-                        unwind_plan_sp->GetSourceName().GetCString());
+    UNWIND_LOG_VERBOSE(log,
+                       "frame uses {0} for full UnwindPlan because we failed "
+                       "to find a call-site unwind plan that would work",
+                       unwind_plan_sp->GetSourceName());
     return unwind_plan_sp;
   }
 
   // If nothing else, use the architectural default UnwindPlan and hope that
   // does the job.
   if (arch_default_unwind_plan_sp)
-    UnwindLogMsgVerbose(
-        "frame uses %s for full UnwindPlan because we are falling back "
-        "to the arch default plan",
-        arch_default_unwind_plan_sp->GetSourceName().GetCString());
+    UNWIND_LOG_VERBOSE(log,
+                       "frame uses {0} for full UnwindPlan because we are "
+                       "falling back to the arch default plan",
+                       arch_default_unwind_plan_sp->GetSourceName());
   else
-    UnwindLogMsg(
-        "Unable to find any UnwindPlan for full unwind of this frame.");
+    UNWIND_LOG(log,
+               "Unable to find any UnwindPlan for full unwind of this frame.");
 
   return arch_default_unwind_plan_sp;
 }
@@ -1144,10 +1160,11 @@ bool RegisterContextUnwind::ReadRegisterValueFromRegisterLocation(
       success = GetNextFrame()->ReadRegister(other_reg_info, value);
     }
     if (success) {
+      Log *log = GetLog(LLDBLog::Unwind);
       UnwindLogMsg("read (%d)'s location", regnum);
       value = value.GetAsUInt64(~0ull, &success) +
               regloc.location.reg_plus_offset.offset;
-      UnwindLogMsg("success %s", success ? "yes" : "no");
+      UNWIND_LOG(log, "success {0}", success ? "yes" : "no");
     }
   } break;
   case UnwindLLDB::ConcreteRegisterLocation::eRegisterValueInferred:
@@ -1357,9 +1374,9 @@ RegisterContextUnwind::GetAbstractRegisterLocation(uint32_t lldb_regnum,
       ExecutionContext exe_ctx(m_thread.shared_from_this());
       active_row->Dump(active_row_strm, m_full_unwind_plan_sp.get(), &m_thread,
                        m_start_pc.GetLoadAddress(exe_ctx.GetTargetPtr()));
-      UnwindLogMsg("Using full unwind plan '%s'",
-                   m_full_unwind_plan_sp->GetSourceName().AsCString(""));
-    ...
[truncated]

``````````

</details>


https://github.com/llvm/llvm-project/pull/191576


More information about the lldb-commits mailing list