go-delve/delve · error

too many arguments in traced function, max is 12 input+retur

Error message

too many arguments in traced function, max is 12 input+return

What it means

When setting up an eBPF/uprobe-based tracepoint (SetUProbe), delve only supports up to 12 arguments total (6 register-passed inputs + 6 return slots) because of the eBPF scratch buffer and calling-convention limits. If the DWARF signature of the traced function requires more than 12 input+return slots, this error is returned and the probe is not installed.

Source

Thrown at pkg/proc/native/proc_linux.go:959

	return linutil.EntryPointFromAuxv(auxvbuf, dbp.bi.Arch.PtrSize()), nil
}

func (dbp *nativeProcess) SetUProbe(fnName string, goidOffset int64, args []ebpf.UProbeArgMap) error {
	// Lazily load and initialize the BPF program upon request to set a uprobe.
	if dbp.os.ebpf == nil {
		var err error
		dbp.os.ebpf, err = ebpf.LoadEBPFTracingProgram(dbp.bi.Images[0].Path)
		if err != nil {
			return err
		}
	}

	// We only allow up to 12 args for a BPF probe.
	// 6 inputs + 6 outputs.
	// Return early if we have more.
	if len(args) > 12 {
		return errors.New("too many arguments in traced function, max is 12 input+return")
	}

	fns := dbp.bi.LookupFunc()[fnName]
	if len(fns) != 1 {
		return &proc.ErrFunctionNotFound{FuncName: fnName}
	}
	fn := fns[0]

	entryPC, err := proc.FirstPCAfterPrologue(dbp, fn, false)
	if err != nil {
		return err
	}

	offset, err := dbp.BinInfo().GStructOffset(dbp.Memory())
	if err != nil {
		return err
	}
	key := entryPC

View on GitHub (pinned to a23773e6c3)

Solutions

  1. Trace a function with fewer parameters, or wrap the call site in a smaller helper function.
  2. Reduce the number of requested return arguments with the trace command.
  3. On amd64, remember only 6 register args are captured — parameters spilled to the stack cannot be traced; restructure the code.
  4. Check the function signature count before calling SetUProbe.

Example fix

// before
func process(a,b,c,d,e,f,g,h,i,j,k,l,m int) {}
dlvs trace process  // error: too many arguments
// after
func process(a,b,c,d,e,f,g,h,i,j,k,l int) {} // <= 12 slots
// or trace a wrapper: func processSmall() { process(1,2,3,4,5,6,7,8,9,10,11,12,13) }
Defensive patterns

Strategy: validation

Validate before calling

// count input + return args before calling SetUProbe
func canTrace(fnName string, numReturns int) error {
	numArgs := countArgsFromDWARF(fnName) // your DWARF/ELF lookup
	if numArgs+numReturns > 12 {
		return fmt.Errorf("%s has %d args+rets; eBPF max is 12", fnName, numArgs+numReturns)
	}
	return nil
}

Type guard

func isTooManyArgsErr(err error) bool {
	return err != nil && strings.Contains(err.Error(), "too many arguments in traced function")
}

Try / catch

err := dlv.SetUProbe(fnName, goidOff, args)
if err != nil && strings.Contains(err.Error(), "too many arguments") {
	// fall back to breakpoint-based tracing instead of eBPF
	return setSoftwareBreakpointTrace(fnName)
}

Prevention

When it happens

Trigger: Calling SetUProbe (via `trace` command or rpc TraceFunction with followCalls/args) on a function whose signature sums to more than 12 input+return arguments.

Common situations: Tracing functions with long parameter lists; passing return-argument slots (`-r`) that push the total over 12; eBPF tracing on linux kernels without alternate arg passing.

Related errors


AI-assisted analysis of go-delve/delve@a23773e6c3 (2026-08-31). Data as JSON: /api/errors/18f5c7305d9c9f74. Report an issue: GitHub.