[PATCH] objtool: Fix another stack overflow in validate_branch()

From: Josh Poimboeuf

Date: Fri Mar 06 2026 - 13:28:23 EST


The insn state is getting saved on the stack twice for each recursive
iteration. No need for that, once is enough.

Fixes the following reported stack overflow:

drivers/scsi/qla2xxx/qla_dbg.o: error: SIGSEGV: objtool stack overflow!
Segmentation fault

Fixes: 70589843b36f ("objtool: Add option to trace function validation")
Reported-by: Arnd Bergmann <arnd@xxxxxxxx>
Closes: https://lore.kernel.org/90956545-2066-46e3-b547-10c884582eb0@xxxxxxxxxxxxxxxx
Signed-off-by: Josh Poimboeuf <jpoimboe@xxxxxxxxxx>
---
tools/objtool/check.c | 10 +++++-----
1 file changed, 5 insertions(+), 5 deletions(-)

diff --git a/tools/objtool/check.c b/tools/objtool/check.c
index 786b2f2adbab..91b3ff4803cf 100644
--- a/tools/objtool/check.c
+++ b/tools/objtool/check.c
@@ -3748,7 +3748,7 @@ static void checksum_update_insn(struct objtool_file *file, struct symbol *func,
static int validate_branch(struct objtool_file *file, struct symbol *func,
struct instruction *insn, struct insn_state state);
static int do_validate_branch(struct objtool_file *file, struct symbol *func,
- struct instruction *insn, struct insn_state state);
+ struct instruction *insn, struct insn_state *state);

static int validate_insn(struct objtool_file *file, struct symbol *func,
struct instruction *insn, struct insn_state *statep,
@@ -4013,7 +4013,7 @@ static int validate_insn(struct objtool_file *file, struct symbol *func,
* tools/objtool/Documentation/objtool.txt.
*/
static int do_validate_branch(struct objtool_file *file, struct symbol *func,
- struct instruction *insn, struct insn_state state)
+ struct instruction *insn, struct insn_state *state)
{
struct instruction *next_insn, *prev_insn = NULL;
bool dead_end;
@@ -4044,7 +4044,7 @@ static int do_validate_branch(struct objtool_file *file, struct symbol *func,
return 1;
}

- ret = validate_insn(file, func, insn, &state, prev_insn, next_insn,
+ ret = validate_insn(file, func, insn, state, prev_insn, next_insn,
&dead_end);

if (!insn->trace) {
@@ -4055,7 +4055,7 @@ static int do_validate_branch(struct objtool_file *file, struct symbol *func,
}

if (!dead_end && !next_insn) {
- if (state.cfi.cfa.base == CFI_UNDEFINED)
+ if (state->cfi.cfa.base == CFI_UNDEFINED)
return 0;
if (file->ignore_unreachables)
return 0;
@@ -4080,7 +4080,7 @@ static int validate_branch(struct objtool_file *file, struct symbol *func,
int ret;

trace_depth_inc();
- ret = do_validate_branch(file, func, insn, state);
+ ret = do_validate_branch(file, func, insn, &state);
trace_depth_dec();

return ret;
--
2.53.0