Skip to content

Commit 81335f9

Browse files
anakryikoAlexei Starovoitov
authored andcommitted
bpf: unconditionally reset backtrack_state masks on global func exit
In mark_chain_precision() logic, when we reach the entry to a global func, it is expected that R1-R5 might be still requested to be marked precise. This would correspond to some integer input arguments being tracked as precise. This is all expected and handled as a special case. What's not expected is that we'll leave backtrack_state structure with some register bits set. This is because for subsequent precision propagations backtrack_state is reused without clearing masks, as all code paths are carefully written in a way to leave empty backtrack_state with zeroed out masks, for speed. The fix is trivial, we always clear register bit in the register mask, and then, optionally, set reg->precise if register is SCALAR_VALUE type. Reported-by: Chris Mason <[email protected]> Fixes: be2ef81 ("bpf: allow precision tracking for programs with subprogs") Signed-off-by: Andrii Nakryiko <[email protected]> Link: https://lore.kernel.org/r/[email protected] Signed-off-by: Alexei Starovoitov <[email protected]>
1 parent b724a64 commit 81335f9

File tree

1 file changed

+3
-5
lines changed

1 file changed

+3
-5
lines changed

kernel/bpf/verifier.c

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -4047,11 +4047,9 @@ static int __mark_chain_precision(struct bpf_verifier_env *env, int regno)
40474047
bitmap_from_u64(mask, bt_reg_mask(bt));
40484048
for_each_set_bit(i, mask, 32) {
40494049
reg = &st->frame[0]->regs[i];
4050-
if (reg->type != SCALAR_VALUE) {
4051-
bt_clear_reg(bt, i);
4052-
continue;
4053-
}
4054-
reg->precise = true;
4050+
bt_clear_reg(bt, i);
4051+
if (reg->type == SCALAR_VALUE)
4052+
reg->precise = true;
40554053
}
40564054
return 0;
40574055
}

0 commit comments

Comments
 (0)