Re: [PATCH bpf-next v6 2/6] bpf: Propagate async callback instructions to scheduling subprograms

Andrii Nakryiko <[email protected]>
Newsgroups org.kernel.vger.bpf
Message-ID <CAEf4BzbX+PDV-uM2qLAh_K0e55oDnhbfRiEd0bFvEmyXfF6Dhw@mail.gmail.com>
On Wed, Aug 5, 2026 at 11:18 AM Eduard Zingerman <[email protected]> wrote:
>
> On Wed, 2026-08-05 at 03:15 +0200, Kumar Kartikeya Dwivedi wrote:
>
> ...
>
> > diff --git a/include/linux/bpf_verifier.h b/include/linux/bpf_verifier.h
> > index 9de45ade473b..42fa464c520f 100644
> > --- a/include/linux/bpf_verifier.h
> > +++ b/include/linux/bpf_verifier.h
> > @@ -447,6 +447,8 @@ static_assert(MAX_BPF_STACK / 8 <= (1 << 6));
> >  struct bpf_verifier_state {
> >       /* call stack tracking */
> >       struct bpf_func_state *frame[MAX_CALL_FRAMES];
> > +     u32 async_stats_subprog_ids[MAX_CALL_FRAMES];
> > +     u32 async_stats_subprog_cnt;
>
> One async callback can call another async callback, e.g. see program
> 'test1' in progs/timer.c. Meaning that this array is not really bound
> by MAX_CALL_FRAMES and the code below may overflow it.
>
> Overall, it seems that having an alternative full call stack solely
> for the purpose of accounting is an overkill. I'd just show async

I agree, it's a bit too much, even though it's useful to be consistent
with non-async callbacks. How about we simplify this just remembering
which entry level subprog (main or global) was active when async cb
was scheduled, and account this async cb to that root program's total?

btw, does anyone remember why we "detach" async cb?

pw-bot: cr


> subprograms as their own roots, tbh. On the other hand, same
> subprogram can be called both as an async and as a regular subprogram :)
> so the idea of a separate spine is not w/o it's merit.
> If we decide to stick with it, maybe pick a better name?
> 'verification_call_stack' or something like this?
>
> If we decide to go with this separate call stack, would it be possible
> to adapt the code in a way that only this call stack is used for
> accounting? (e.g. is filled on regular subprogram calls etc).
>
> Another option is to build an implicit call graph in env while
> verifying and count only self instructions and counters on edges.
> Then propagate the data over the graph in post-order traversal
> (subprog_topo_order is already computed). I think I like this idea
> the most.
>
> ...
>
> > @@ -2293,6 +2298,12 @@ static struct bpf_verifier_state *push_async_cb(struct bpf_verifier_env *env,
> >                       0 /* frameno within this callchain */,
> >                       subprog /* subprog number within this prog */);
> >       elem->st.frame[0] = frame;
> > +     cnt = env->cur_state->async_stats_subprog_cnt;
> > +     memcpy(elem->st.async_stats_subprog_ids, env->cur_state->async_stats_subprog_ids,
> > +            cnt * sizeof(elem->st.async_stats_subprog_ids[0]));
> > +     for (i = 0; i <= env->cur_state->curframe; i++)
> > +             elem->st.async_stats_subprog_ids[cnt++] = env->cur_state->frame[i]->subprogno;
> > +     elem->st.async_stats_subprog_cnt = cnt;
> >       return &elem->st;
> >  }
>
> ...
>
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.