Commit be7dbd27 authored by Andrii Nakryiko's avatar Andrii Nakryiko Committed by Alexei Starovoitov

selftests/bpf: avoid mark_all_scalars_precise() trigger in one of iter tests

iter_pass_iter_ptr_to_subprog subtest is relying on actual array size
being passed as subprog parameter. This combined with recent fixes to
precision tracking in conditional jumps ([0]) is now causing verifier to
backtrack all the way to the point where sum() and fill() subprogs are
called, at which point precision backtrack bails out and forces all the
states to have precise SCALAR registers. This in turn causes each
possible value of i within fill() and sum() subprogs to cause
a different non-equivalent state, preventing iterator code to converge.

For now, change the test to assume fixed size of passed in array. Once
BPF verifier supports precision tracking across subprogram calls, these
changes will be reverted as unnecessary.

  [0] 71b547f5 ("bpf: Fix incorrect verifier pruning due to missing register precision taints")
Signed-off-by: default avatarAndrii Nakryiko <andrii@kernel.org>
Link: https://lore.kernel.org/r/20230424235128.1941726-1-andrii@kernel.orgSigned-off-by: default avatarAlexei Starovoitov <ast@kernel.org>
parent a0c109dc
...@@ -651,25 +651,29 @@ int iter_stack_array_loop(const void *ctx) ...@@ -651,25 +651,29 @@ int iter_stack_array_loop(const void *ctx)
return sum; return sum;
} }
static __noinline void fill(struct bpf_iter_num *it, int *arr, __u32 n, int mul) #define ARR_SZ 16
static __noinline void fill(struct bpf_iter_num *it, int *arr, int mul)
{ {
int *t, i; int *t;
__u64 i;
while ((t = bpf_iter_num_next(it))) { while ((t = bpf_iter_num_next(it))) {
i = *t; i = *t;
if (i >= n) if (i >= ARR_SZ)
break; break;
arr[i] = i * mul; arr[i] = i * mul;
} }
} }
static __noinline int sum(struct bpf_iter_num *it, int *arr, __u32 n) static __noinline int sum(struct bpf_iter_num *it, int *arr)
{ {
int *t, i, sum = 0;; int *t, sum = 0;;
__u64 i;
while ((t = bpf_iter_num_next(it))) { while ((t = bpf_iter_num_next(it))) {
i = *t; i = *t;
if (i >= n) if (i >= ARR_SZ)
break; break;
sum += arr[i]; sum += arr[i];
} }
...@@ -681,7 +685,7 @@ SEC("raw_tp") ...@@ -681,7 +685,7 @@ SEC("raw_tp")
__success __success
int iter_pass_iter_ptr_to_subprog(const void *ctx) int iter_pass_iter_ptr_to_subprog(const void *ctx)
{ {
int arr1[16], arr2[32]; int arr1[ARR_SZ], arr2[ARR_SZ];
struct bpf_iter_num it; struct bpf_iter_num it;
int n, sum1, sum2; int n, sum1, sum2;
...@@ -690,25 +694,25 @@ int iter_pass_iter_ptr_to_subprog(const void *ctx) ...@@ -690,25 +694,25 @@ int iter_pass_iter_ptr_to_subprog(const void *ctx)
/* fill arr1 */ /* fill arr1 */
n = ARRAY_SIZE(arr1); n = ARRAY_SIZE(arr1);
bpf_iter_num_new(&it, 0, n); bpf_iter_num_new(&it, 0, n);
fill(&it, arr1, n, 2); fill(&it, arr1, 2);
bpf_iter_num_destroy(&it); bpf_iter_num_destroy(&it);
/* fill arr2 */ /* fill arr2 */
n = ARRAY_SIZE(arr2); n = ARRAY_SIZE(arr2);
bpf_iter_num_new(&it, 0, n); bpf_iter_num_new(&it, 0, n);
fill(&it, arr2, n, 10); fill(&it, arr2, 10);
bpf_iter_num_destroy(&it); bpf_iter_num_destroy(&it);
/* sum arr1 */ /* sum arr1 */
n = ARRAY_SIZE(arr1); n = ARRAY_SIZE(arr1);
bpf_iter_num_new(&it, 0, n); bpf_iter_num_new(&it, 0, n);
sum1 = sum(&it, arr1, n); sum1 = sum(&it, arr1);
bpf_iter_num_destroy(&it); bpf_iter_num_destroy(&it);
/* sum arr2 */ /* sum arr2 */
n = ARRAY_SIZE(arr2); n = ARRAY_SIZE(arr2);
bpf_iter_num_new(&it, 0, n); bpf_iter_num_new(&it, 0, n);
sum2 = sum(&it, arr2, n); sum2 = sum(&it, arr2);
bpf_iter_num_destroy(&it); bpf_iter_num_destroy(&it);
bpf_printk("sum1=%d, sum2=%d", sum1, sum2); bpf_printk("sum1=%d, sum2=%d", sum1, sum2);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment