Skip to content

Commit cdbd90f

Browse files
fixup! Use Expected to propagate error messages
1 parent 130728a commit cdbd90f

File tree

1 file changed

+52
-32
lines changed

1 file changed

+52
-32
lines changed

lldb/source/Plugins/LanguageRuntime/Swift/SwiftLanguageRuntime.cpp

Lines changed: 52 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -2589,45 +2589,49 @@ lldb::addr_t SwiftLanguageRuntime::GetAsyncContext(RegisterContext *regctx) {
25892589
}
25902590

25912591
/// Functional wrapper to read a register as an address.
2592-
static std::optional<addr_t> ReadRegisterAsAddress(RegisterContext &regctx,
2593-
RegisterKind regkind,
2594-
unsigned regnum) {
2592+
static llvm::Expected<addr_t> ReadRegisterAsAddress(RegisterContext &regctx,
2593+
RegisterKind regkind,
2594+
unsigned regnum) {
25952595
unsigned lldb_regnum =
25962596
regctx.ConvertRegisterKindToRegisterNumber(regkind, regnum);
25972597
auto reg = regctx.ReadRegisterAsUnsigned(lldb_regnum, LLDB_INVALID_ADDRESS);
25982598
if (reg != LLDB_INVALID_ADDRESS)
25992599
return reg;
2600-
return {};
2600+
return llvm::createStringError(
2601+
"SwiftLanguageRuntime: failed to read register from regctx");
26012602
}
26022603

26032604
/// Functional wrapper to read a pointer from process memory at `addr +
26042605
/// offset`.
2605-
static std::optional<addr_t>
2606-
ReadPtrFromAddr(Process &process, std::optional<addr_t> addr, int offset = 0) {
2606+
static llvm::Expected<addr_t>
2607+
ReadPtrFromAddr(Process &process, llvm::Expected<addr_t> addr, int offset = 0) {
26072608
if (!addr)
2608-
return {};
2609+
return addr;
26092610
Status error;
26102611
addr_t ptr = process.ReadPointerFromMemory(*addr + offset, error);
26112612
if (ptr != LLDB_INVALID_ADDRESS)
26122613
return ptr;
2613-
return {};
2614+
return llvm::createStringError("SwiftLanguageRuntime: Failed to read ptr "
2615+
"from memory address 0x%8.8" PRIx64,
2616+
*addr + offset);
26142617
}
26152618

26162619
/// Computes the Canonical Frame Address (CFA) by converting the abstract
26172620
/// location of UnwindPlan::Row::FAValue into a concrete address. This is a
26182621
/// simplified version of the methods in RegisterContextUnwind, since plumbing
26192622
/// access to those here would be challenging.
2620-
static std::optional<addr_t> GetCFA(Process &process, RegisterContext &regctx,
2621-
RegisterKind regkind,
2622-
UnwindPlan::Row::FAValue cfa_loc) {
2623+
static llvm::Expected<addr_t> GetCFA(Process &process, RegisterContext &regctx,
2624+
RegisterKind regkind,
2625+
UnwindPlan::Row::FAValue cfa_loc) {
26232626
using ValueType = UnwindPlan::Row::FAValue::ValueType;
26242627
switch (cfa_loc.GetValueType()) {
26252628
case ValueType::isRegisterPlusOffset: {
26262629
unsigned regnum = cfa_loc.GetRegisterNumber();
2627-
if (std::optional<addr_t> regvalue =
2630+
if (llvm::Expected<addr_t> regvalue =
26282631
ReadRegisterAsAddress(regctx, regkind, regnum))
26292632
return *regvalue + cfa_loc.GetOffset();
2630-
break;
2633+
else
2634+
return regvalue;
26312635
}
26322636
case ValueType::isConstant:
26332637
case ValueType::isDWARFExpression:
@@ -2636,27 +2640,34 @@ static std::optional<addr_t> GetCFA(Process &process, RegisterContext &regctx,
26362640
case ValueType::unspecified:
26372641
break;
26382642
}
2639-
return {};
2643+
return llvm::createStringError(
2644+
"SwiftLanguageRuntime: Unsupported FA location type = %d",
2645+
cfa_loc.GetValueType());
26402646
}
26412647

26422648
/// Attempts to use UnwindPlans that inspect assembly to recover the entry value
26432649
/// of the async context register. This is a simplified version of the methods
26442650
/// in RegisterContextUnwind, since plumbing access to those here would be
26452651
/// challenging.
2646-
static std::optional<addr_t> ReadAsyncContextRegisterFromUnwind(
2652+
static llvm::Expected<addr_t> ReadAsyncContextRegisterFromUnwind(
26472653
SymbolContext &sc, Process &process, Address pc, Address func_start_addr,
26482654
RegisterContext &regctx, AsyncUnwindRegisterNumbers regnums) {
26492655
FuncUnwindersSP unwinders =
26502656
pc.GetModule()->GetUnwindTable().GetFuncUnwindersContainingAddress(pc,
26512657
sc);
26522658
if (!unwinders)
2653-
return {};
2659+
return llvm::createStringError("SwiftLanguageRuntime: Failed to find "
2660+
"function unwinder at address 0x%8.8" PRIx64,
2661+
pc.GetFileAddress());
26542662

26552663
Target &target = process.GetTarget();
26562664
UnwindPlanSP unwind_plan =
26572665
unwinders->GetUnwindPlanAtNonCallSite(target, regctx.GetThread());
26582666
if (!unwind_plan)
2659-
return {};
2667+
return llvm::createStringError(
2668+
"SwiftLanguageRuntime: Failed to find non call site unwind plan at "
2669+
"address 0x%8.8" PRIx64,
2670+
pc.GetFileAddress());
26602671

26612672
const RegisterKind unwind_regkind = unwind_plan->GetRegisterKind();
26622673
UnwindPlan::RowSP row = unwind_plan->GetRowForFunctionOffset(
@@ -2668,7 +2679,8 @@ static std::optional<addr_t> ReadAsyncContextRegisterFromUnwind(
26682679
if (!regctx.ConvertBetweenRegisterKinds(
26692680
regnums.GetRegisterKind(), regnums.async_ctx_regnum, unwind_regkind,
26702681
async_reg_unwind_regdomain))
2671-
return {};
2682+
return llvm::createStringError(
2683+
"SwiftLanguageRuntime: Failed to convert register domains");
26722684

26732685
// If the plan doesn't have information about the async register, we can use
26742686
// its current value, as this is a callee saved register.
@@ -2689,16 +2701,16 @@ static std::optional<addr_t> ReadAsyncContextRegisterFromUnwind(
26892701
return ReadRegisterAsAddress(regctx, unwind_regkind, regnum);
26902702
}
26912703
case RestoreType::atCFAPlusOffset: {
2692-
std::optional<addr_t> cfa =
2704+
llvm::Expected<addr_t> cfa =
26932705
GetCFA(process, regctx, unwind_regkind, row->GetCFAValue());
2694-
return ReadPtrFromAddr(process, cfa, regloc.GetOffset());
2706+
return ReadPtrFromAddr(process, std::move(cfa), regloc.GetOffset());
26952707
}
26962708
case RestoreType::isCFAPlusOffset: {
2697-
std::optional<addr_t> cfa =
2698-
GetCFA(process, regctx, unwind_regkind, row->GetCFAValue());
2699-
if (!cfa)
2700-
return {};
2701-
return *cfa + regloc.GetOffset();
2709+
if (llvm::Expected<addr_t> cfa =
2710+
GetCFA(process, regctx, unwind_regkind, row->GetCFAValue()))
2711+
return *cfa + regloc.GetOffset();
2712+
else
2713+
return cfa;
27022714
}
27032715
case RestoreType::isConstant:
27042716
return regloc.GetConstant();
@@ -2708,9 +2720,10 @@ static std::optional<addr_t> ReadAsyncContextRegisterFromUnwind(
27082720
case RestoreType::isAFAPlusOffset:
27092721
case RestoreType::isDWARFExpression:
27102722
case RestoreType::atDWARFExpression:
2711-
return {};
2723+
break;
27122724
}
2713-
return {};
2725+
return llvm::createStringError(
2726+
"SwiftLanguageRuntime: Unsupported register location type = %d", loctype);
27142727
}
27152728

27162729
// Examine the register state and detect the transition from a real
@@ -2721,6 +2734,11 @@ SwiftLanguageRuntime::GetRuntimeUnwindPlan(ProcessSP process_sp,
27212734
RegisterContext *regctx,
27222735
bool &behaves_like_zeroth_frame) {
27232736
LLDB_SCOPED_TIMER();
2737+
auto log_expected = [](llvm::Error error) {
2738+
Log *log = GetLog(LLDBLog::Unwind);
2739+
LLDB_LOG_ERROR(log, std::move(error), "SwiftLanguageRuntime: error {0}");
2740+
return UnwindPlanSP();
2741+
};
27242742

27252743
Target &target(process_sp->GetTarget());
27262744
auto arch = target.GetArchitecture();
@@ -2771,12 +2789,14 @@ SwiftLanguageRuntime::GetRuntimeUnwindPlan(ProcessSP process_sp,
27712789
bool indirect_context =
27722790
IsSwiftAsyncAwaitResumePartialFunctionSymbol(mangled_name.GetStringRef());
27732791

2774-
std::optional<addr_t> async_reg = ReadAsyncContextRegisterFromUnwind(
2792+
llvm::Expected<addr_t> async_reg = ReadAsyncContextRegisterFromUnwind(
27752793
sc, *process_sp, pc, func_start_addr, *regctx, *regnums);
2776-
std::optional<addr_t> async_ctx =
2777-
indirect_context ? ReadPtrFromAddr(*m_process, async_reg) : async_reg;
2778-
if (!async_reg || !async_ctx)
2779-
return UnwindPlanSP();
2794+
if (!async_reg)
2795+
return log_expected(async_reg.takeError());
2796+
llvm::Expected<addr_t> async_ctx =
2797+
indirect_context ? ReadPtrFromAddr(*m_process, *async_reg) : *async_reg;
2798+
if (!async_ctx)
2799+
return log_expected(async_ctx.takeError());
27802800

27812801
UnwindPlan::RowSP row(new UnwindPlan::Row);
27822802
const int32_t ptr_size = 8;

0 commit comments

Comments
 (0)