All of lore.kernel.org
 help / color / mirror / Atom feed
From: Hao Luo <haoluo@google.com>
To: Alexei Starovoitov <alexei.starovoitov@gmail.com>
Cc: Andrii Nakryiko <andrii.nakryiko@gmail.com>,
	Alexei Starovoitov <ast@kernel.org>,
	Andrii Nakryiko <andrii@kernel.org>,
	Daniel Borkmann <daniel@iogearbox.net>,
	Martin KaFai Lau <kafai@fb.com>, Song Liu <songliubraving@fb.com>,
	Yonghong Song <yhs@fb.com>, KP Singh <kpsingh@kernel.org>,
	bpf <bpf@vger.kernel.org>
Subject: Re: [PATCH bpf-next v1 4/9] bpf: Replace PTR_TO_XXX_OR_NULL with PTR_TO_XXX | PTR_MAYBE_NULL
Date: Thu, 16 Dec 2021 16:32:41 -0800	[thread overview]
Message-ID: <CA+khW7gEsRcz7CVcb9BZ_-o2su+cE-wRu8om0EcNbEG_d0mPUg@mail.gmail.com> (raw)
In-Reply-To: <CAADnVQJTQ9f5V_-=kWa79ojvVLWFX2YLsRHLKOa9MZUB0gYa9A@mail.gmail.com>

On Sun, Dec 12, 2021 at 6:03 PM Alexei Starovoitov
<alexei.starovoitov@gmail.com> wrote:
>
> On Sun, Dec 12, 2021 at 5:51 PM Alexei Starovoitov
> <alexei.starovoitov@gmail.com> wrote:
> >
> > On Fri, Dec 10, 2021 at 11:56 AM Hao Luo <haoluo@google.com> wrote:
> > >
> > > On Thu, Dec 9, 2021 at 1:45 PM Alexei Starovoitov
> > > <alexei.starovoitov@gmail.com> wrote:
> > > >
> > > > On Wed, Dec 8, 2021 at 12:04 PM Andrii Nakryiko
> > > > <andrii.nakryiko@gmail.com> wrote:
> > > > >
> > > > > > > > +static const char *reg_type_str(enum bpf_reg_type type)
> > > > > > > > +{
> > > > > > > > +       static const char * const str[] = {
> > > > > > > > +               [NOT_INIT]              = "?",
> > > > > > > > +               [SCALAR_VALUE]          = "inv",
> > > > > > > > +               [PTR_TO_CTX]            = "ctx",
> > > > > > > > +               [CONST_PTR_TO_MAP]      = "map_ptr",
> > > > > > > > +               [PTR_TO_MAP_VALUE]      = "map_value",
> > > > > > > > +               [PTR_TO_STACK]          = "fp",
> > > > > > > > +               [PTR_TO_PACKET]         = "pkt",
> > > > > > > > +               [PTR_TO_PACKET_META]    = "pkt_meta",
> > > > > > > > +               [PTR_TO_PACKET_END]     = "pkt_end",
> > > > > > > > +               [PTR_TO_FLOW_KEYS]      = "flow_keys",
> > > > > > > > +               [PTR_TO_SOCKET]         = "sock",
> > > > > > > > +               [PTR_TO_SOCK_COMMON]    = "sock_common",
> > > > > > > > +               [PTR_TO_TCP_SOCK]       = "tcp_sock",
> > > > > > > > +               [PTR_TO_TP_BUFFER]      = "tp_buffer",
> > > > > > > > +               [PTR_TO_XDP_SOCK]       = "xdp_sock",
> > > > > > > > +               [PTR_TO_BTF_ID]         = "ptr_",
> > > > > > > > +               [PTR_TO_PERCPU_BTF_ID]  = "percpu_ptr_",
> > > > > > > > +               [PTR_TO_MEM]            = "mem",
> > > > > > > > +               [PTR_TO_RDONLY_BUF]     = "rdonly_buf",
> > > > > > > > +               [PTR_TO_RDWR_BUF]       = "rdwr_buf",
> > > > > > > > +               [PTR_TO_FUNC]           = "func",
> > > > > > > > +               [PTR_TO_MAP_KEY]        = "map_key",
> > > > > > > > +       };
> > > > > > > > +
> > > > > > > > +       return str[base_type(type)];
> > > > > > >
> > > > > > > well... now we lose the "_or_null" part, that can be pretty important.
> > > > > > > Same will happen with RDONLY flag, right?
> > > > > > >
> > > > > > > What can we do about that?
> > > > > > >
> > > > > >
> > > > > > We can format the string into a global buffer and return the buffer to
> > > > > > the caller. A little overhead on string formatting.
> > > > >
> > > > > Can't use global buffer, because multiple BPF verifications can
> > > > > proceed at the same time.
> > > >
> > > > I think reg_type_str() can still return a const char string
> > > > with flags.
> > > > It's not going to be a direct str[base_type(type)]; of course.
> > > > The str[] would be different.
> > >
> > > Sorry I didn't fully grasp this comment. Following is my understanding
> > > and thoughts so far. Let me know if I missed anything.
> >
> > I meant that for now we can do:
> >
> > static const char * const str[] = {
> >    [NOT_INIT]              = "?",
> >    [PTR_TO_RDONLY_BUF]     = "rdonly_buf",
> > };
> > switch(type) {
> >   case PTR_TO_RDONLY_BUF | MAYBE_NULL:return "rdonly_buf_or_null";
> >   default: return str[base_type(type)];
> > }
> >
> > > Right, we can return a char string, but the string must be provided by
> > > the caller, which is the annoying part. We could do something as
> > > following (solution 1)
> > >
> > > const char *reg_type_str(..., char *buf)
> > > {
> > >   ...
> > >   snprintf(buf, ...);
> > >   return buf;
> > > }
> > >
> > > OR, (solution 2) we may embed a buffer in bpf_verifier_env and pass
> > > env into reg_type_str(). reg_type_str() just returns the buffer in
> > > env. This doesn't require the caller to prepare the buffer.
> > >
> > > const char *reg_type_str(..., env)
> > > {
> > >   ...
> > >   snprintf(env->buf, ...);
> > >   return env->buf;
> > > }
> >
> > If we go with this approach then passing 'env' is a bit better,
> > since 'buf' doesn't need to be allocated on stack.
> >
> > > However, there will be a caveat when there are more than one
> > > reg_type_str in one verbose statement. In solution 1, the input buf
> > > has to be different. In solution 2, we just can't do that, because the
> > > buffer is implicitly shared. What do you think about solution 2?
> >
> > There is only one verbose() with two reg_type_str[] right now.
> > It can easily be split into two verbose().
> >
> > > >
> > > > If that doesn't work out we can try:
> > > > s/verbose(,"%s", reg_type_str[])
> > > > /verbose(, "%s%s", reg_type_str(), reg_type_flags_str())
> > >
> > > This is probably more cumbersome IMHO.
> > >
> > > Thinking about the implementation of reg_type_flags_str(). Because
> > > flags can be combined, I think it would be better to format a dynamic
> > > buffer, then we are back to the same problem: caller needs to pass a
> > > buffer. Of course, with only two flags right now, we could enumerate
> > > all flag combinations and map them to const strings.
> >
> > Yeah. With 3 or more flags that can be combined the const char approach
> > wouldn't scale. So let's try 'env' approach?
> >
> > The only tweak is that 'log' would be better than 'env'.
> > That temp buf can be in struct bpf_verifier_log *log.
>
> Another idea would be to add bpf specific modifiers in
> pointer() in lib/vsprintf.c for verifier's reg_state, reg_type,
> and other bpf structs.
> It might make print_verifier_state() much cleaner and
> would allow easy printing of reg state from anywhere inside
> the verifier code.
> Currently the error print has minimal info. Like:
>   verbose(env, "R%d invalid %s access off=%d size=%d\n",
>           regno, reg_type_str[reg->type], off, size);
> With vsnprintf support we could do something like:
>   verbose(env, "%Brp invalid access off=%d size=%d\n",
>           reg, off, size);
> and pointer() will do full print of struct bpf_reg_state.
>
> This is probably something to consider long term.

ACK. Thanks for the comments. The 'env' proposal looks reasonably
well. I sent out v2. Please take a look there.

  reply	other threads:[~2021-12-17  0:32 UTC|newest]

Thread overview: 32+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2021-12-06 23:22 [PATCH bpf-next v1 0/9] Introduce composable bpf types Hao Luo
2021-12-06 23:22 ` [PATCH bpf-next v1 1/9] bpf: Introduce composable reg, ret and arg types Hao Luo
2021-12-06 23:22 ` [PATCH bpf-next v1 2/9] bpf: Replace ARG_XXX_OR_NULL with ARG_XXX | PTR_MAYBE_NULL Hao Luo
2021-12-07  5:45   ` Andrii Nakryiko
2021-12-07 18:52     ` Hao Luo
2021-12-06 23:22 ` [PATCH bpf-next v1 3/9] bpf: Replace RET_XXX_OR_NULL with RET_XXX " Hao Luo
2021-12-07  5:51   ` Andrii Nakryiko
2021-12-07 19:05     ` Hao Luo
2021-12-06 23:22 ` [PATCH bpf-next v1 4/9] bpf: Replace PTR_TO_XXX_OR_NULL with PTR_TO_XXX " Hao Luo
2021-12-07  6:08   ` Andrii Nakryiko
2021-12-08  3:37     ` Hao Luo
2021-12-08 20:03       ` Andrii Nakryiko
2021-12-09 21:45         ` Alexei Starovoitov
2021-12-10 19:56           ` Hao Luo
2021-12-13  1:51             ` Alexei Starovoitov
2021-12-13  2:02               ` Alexei Starovoitov
2021-12-17  0:32                 ` Hao Luo [this message]
2021-12-06 23:22 ` [PATCH bpf-next v1 5/9] bpf: Introduce MEM_RDONLY flag Hao Luo
2021-12-07  6:14   ` Andrii Nakryiko
2021-12-08  3:41     ` Hao Luo
2021-12-06 23:22 ` [PATCH bpf-next v1 6/9] bpf: Convert PTR_TO_MEM_OR_NULL to composable types Hao Luo
2021-12-06 23:22 ` [PATCH bpf-next v1 7/9] bpf: Make per_cpu_ptr return rdonly PTR_TO_MEM Hao Luo
2021-12-07  6:18   ` Andrii Nakryiko
2021-12-08  3:54     ` Hao Luo
2021-12-10 17:42       ` Andrii Nakryiko
2021-12-10 18:36         ` Hao Luo
2021-12-06 23:22 ` [PATCH bpf-next v1 8/9] bpf: Add MEM_RDONLY for helper args that are pointers to rdonly mem Hao Luo
2021-12-07  6:23   ` Andrii Nakryiko
2021-12-08  3:49     ` Hao Luo
2021-12-09 20:04       ` Hao Luo
2021-12-10 17:55         ` Andrii Nakryiko
2021-12-06 23:22 ` [PATCH bpf-next v1 9/9] bpf/selftests: Test PTR_TO_RDONLY_MEM Hao Luo

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=CA+khW7gEsRcz7CVcb9BZ_-o2su+cE-wRu8om0EcNbEG_d0mPUg@mail.gmail.com \
    --to=haoluo@google.com \
    --cc=alexei.starovoitov@gmail.com \
    --cc=andrii.nakryiko@gmail.com \
    --cc=andrii@kernel.org \
    --cc=ast@kernel.org \
    --cc=bpf@vger.kernel.org \
    --cc=daniel@iogearbox.net \
    --cc=kafai@fb.com \
    --cc=kpsingh@kernel.org \
    --cc=songliubraving@fb.com \
    --cc=yhs@fb.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.