{"record":{"id":"465fdf80db6429e8","repo":"go-delve/delve","slug":"cannot-establish-frame-at-uprobe-pc-x-w","errorCode":null,"errorMessage":"cannot establish frame at uprobe PC %#x: %w","messagePattern":"cannot establish frame at uprobe PC %#x: %w","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"pkg/proc/breakpoints.go","lineNumber":710,"sourceCode":"\n// uprobeEntryPointCFA returns the uprobe PC (FirstPCAfterPrologue) and\n// the CFA-from-RSP offset at that PC (i.e. the constant N in CFA = RSP + N).\n// This offset is used as inputRegs.CFA when evaluating DWARF locations for\n// input parameters so that DW_OP_fbreg expressions yield RSP-relative offsets\n// directly — see the comment in setEBPFTracepointOnFunc for the full derivation.\nfunc uprobeEntryPointCFA(t *Target, fn *Function) (uint64, int64, error) {\n\tuprobePC, err := FirstPCAfterPrologue(t, fn, false)\n\tif err != nil {\n\t\treturn 0, 0, err\n\t}\n\tbi := t.BinInfo()\n\tfde, err := bi.frameEntries.FDEForPC(uprobePC)\n\tif err != nil {\n\t\treturn 0, 0, fmt.Errorf(\"no FDE for uprobe PC %#x: %w\", uprobePC, err)\n\t}\n\tframectx, err := fde.EstablishFrame(uprobePC)\n\tif err != nil {\n\t\treturn 0, 0, fmt.Errorf(\"cannot establish frame at uprobe PC %#x: %w\", uprobePC, err)\n\t}\n\tif framectx.CFA.Rule != frame.RuleCFA {\n\t\treturn 0, 0, fmt.Errorf(\"unexpected CFA rule %d at uprobe PC %#x\", framectx.CFA.Rule, uprobePC)\n\t}\n\treturn uprobePC, framectx.CFA.Offset, nil\n}\n\n// SetWatchpoint sets a data breakpoint at addr and stores it in the\n// process wide break point table.\nfunc (t *Target) SetWatchpoint(logicalID int, scope *EvalScope, expr string, wtype WatchType, cond ast.Expr) (*Breakpoint, error) {\n\tif (wtype&WatchWrite == 0) && (wtype&WatchRead == 0) {\n\t\treturn nil, errors.New(\"at least one of read and write must be set for watchpoint\")\n\t}\n\n\tn, err := parser.ParseExpr(expr)\n\tif err != nil {\n\t\treturn nil, err\n\t}","sourceCodeStart":692,"sourceCodeEnd":728,"githubUrl":"https://github.com/go-delve/delve/blob/a23773e6c31361e43246bc43a424ee009679b174/pkg/proc/breakpoints.go#L692-L728","documentation":"After finding the FDE for the uprobe PC, Delve calls fde.EstablishFrame to build the frame context at that exact instruction. If EstablishFrame fails (malformed or incomplete CFI program at that address), the CFA offset required for the uprobe argument layout cannot be computed, so the eBPF tracepoint setup fails.","triggerScenarios":"setEBPFTracepointOnFunc on a function whose FDE exists but whose CFI program cannot be evaluated at uprobePC — corrupt/truncated .debug_frame, unsupported DWARF CFI opcodes, or a PC inside an exotic prologue region.","commonSituations":"Binaries produced by toolchains emitting DWARF variants Delve's frame parser doesn't fully support; uprobe placed mid-prologue where the frame description has no rule yet; mixing C/asm objects with different DWARF versions.","solutions":["Retry with the latest Delve version (DWARF CFI parser gains opcode support over time)","Trace a different function or adjust the tracepoint to FirstPCAfterPrologue via the normal API rather than fn.Entry","Recompile with a standard Go toolchain and DWARF enabled (no -w) to get well-formed frame data","Fall back to the non-eBPF trace backend"],"exampleFix":"// before\ndlv trace --ebpf myAsmWrapper\n// after\ndlv trace myAsmWrapper  // software tracepoint backend","handlingStrategy":"fallback","validationCode":"fde, err := bi.frameEntries.FDEForPC(pc)\nif err == nil {\n    if _, err := fde.EstablishFrame(pc); err != nil { /* fallback to software tracepoint */ }\n}","typeGuard":null,"tryCatchPattern":"if err != nil && strings.Contains(err.Error(), \"cannot establish frame at uprobe PC\") {\n    log.Printf(\"CFI unusable at %#x, falling back\", uprobePC)\n    return setSoftwareTracepoint(t, fn)\n}","preventionTips":["Keep the Go toolchain and Delve versions current (DWARF parser fixes)","Avoid mixing hand-written asm objects into the traced function's package","Confirm the FDE covers the exact PC, not just the function entry","Use the default trace backend when CFI integrity is uncertain"],"tags":["ebpf","dwarf","unwind","frame"],"backgroundTag":"cfi-establish-frame-failed","analyzedSha":"a23773e6c31361e43246bc43a424ee009679b174","analyzedAt":"2026-08-31T15:12:45.221Z","schemaVersion":2},"datasetVersion":"2026-08-31T19:17:28.585Z"}