Re: [PATCH bpf-next v4 01/12] bpf: Refactor bprintf buffer support

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On Tue, Jul 1, 2025 at 11:17 PM Kumar Kartikeya Dwivedi
<memxor@xxxxxxxxx> wrote:
>
> Refactor code to be able to get and put bprintf buffers and use
> bpf_printf_prepare independently. This will be used in the next patch to
> implement BPF streams support, particularly as a staging buffer for
> strings that need to be formatted and then allocated and pushed into a
> stream.
>
> Signed-off-by: Kumar Kartikeya Dwivedi <memxor@xxxxxxxxx>
> ---
>  include/linux/bpf.h  | 15 ++++++++++++++-
>  kernel/bpf/helpers.c | 26 +++++++++++---------------
>  2 files changed, 25 insertions(+), 16 deletions(-)
>

Reviewed-by: Emil Tsalapatis <emil@xxxxxxxxxxxxxxx>

> diff --git a/include/linux/bpf.h b/include/linux/bpf.h
> index 5dd556e89cce..4fff0cee8622 100644
> --- a/include/linux/bpf.h
> +++ b/include/linux/bpf.h
> @@ -3550,6 +3550,16 @@ bool btf_id_set_contains(const struct btf_id_set *set, u32 id);
>  #define MAX_BPRINTF_VARARGS            12
>  #define MAX_BPRINTF_BUF                        1024
>
> +/* Per-cpu temp buffers used by printf-like helpers to store the bprintf binary
> + * arguments representation.
> + */
> +#define MAX_BPRINTF_BIN_ARGS   512
> +
> +struct bpf_bprintf_buffers {
> +       char bin_args[MAX_BPRINTF_BIN_ARGS];
> +       char buf[MAX_BPRINTF_BUF];
> +};
> +
>  struct bpf_bprintf_data {
>         u32 *bin_args;
>         char *buf;
> @@ -3557,9 +3567,12 @@ struct bpf_bprintf_data {
>         bool get_buf;
>  };
>
> -int bpf_bprintf_prepare(char *fmt, u32 fmt_size, const u64 *raw_args,
> +int bpf_bprintf_prepare(const char *fmt, u32 fmt_size, const u64 *raw_args,
>                         u32 num_args, struct bpf_bprintf_data *data);
>  void bpf_bprintf_cleanup(struct bpf_bprintf_data *data);
> +int bpf_try_get_buffers(struct bpf_bprintf_buffers **bufs);
> +void bpf_put_buffers(void);
> +
>
>  #ifdef CONFIG_BPF_LSM
>  void bpf_cgroup_atype_get(u32 attach_btf_id, int cgroup_atype);
> diff --git a/kernel/bpf/helpers.c b/kernel/bpf/helpers.c
> index f48fa3fe8dec..8f1cc1d525db 100644
> --- a/kernel/bpf/helpers.c
> +++ b/kernel/bpf/helpers.c
> @@ -764,22 +764,13 @@ static int bpf_trace_copy_string(char *buf, void *unsafe_ptr, char fmt_ptype,
>         return -EINVAL;
>  }
>
> -/* Per-cpu temp buffers used by printf-like helpers to store the bprintf binary
> - * arguments representation.
> - */
> -#define MAX_BPRINTF_BIN_ARGS   512
> -
>  /* Support executing three nested bprintf helper calls on a given CPU */
>  #define MAX_BPRINTF_NEST_LEVEL 3
> -struct bpf_bprintf_buffers {
> -       char bin_args[MAX_BPRINTF_BIN_ARGS];
> -       char buf[MAX_BPRINTF_BUF];
> -};
>
>  static DEFINE_PER_CPU(struct bpf_bprintf_buffers[MAX_BPRINTF_NEST_LEVEL], bpf_bprintf_bufs);
>  static DEFINE_PER_CPU(int, bpf_bprintf_nest_level);
>
> -static int try_get_buffers(struct bpf_bprintf_buffers **bufs)
> +int bpf_try_get_buffers(struct bpf_bprintf_buffers **bufs)
>  {
>         int nest_level;
>
> @@ -795,16 +786,21 @@ static int try_get_buffers(struct bpf_bprintf_buffers **bufs)
>         return 0;
>  }
>
> -void bpf_bprintf_cleanup(struct bpf_bprintf_data *data)
> +void bpf_put_buffers(void)
>  {
> -       if (!data->bin_args && !data->buf)
> -               return;
>         if (WARN_ON_ONCE(this_cpu_read(bpf_bprintf_nest_level) == 0))
>                 return;
>         this_cpu_dec(bpf_bprintf_nest_level);
>         preempt_enable();
>  }
>
> +void bpf_bprintf_cleanup(struct bpf_bprintf_data *data)
> +{
> +       if (!data->bin_args && !data->buf)
> +               return;
> +       bpf_put_buffers();
> +}
> +
>  /*
>   * bpf_bprintf_prepare - Generic pass on format strings for bprintf-like helpers
>   *
> @@ -819,7 +815,7 @@ void bpf_bprintf_cleanup(struct bpf_bprintf_data *data)
>   * In argument preparation mode, if 0 is returned, safe temporary buffers are
>   * allocated and bpf_bprintf_cleanup should be called to free them after use.
>   */
> -int bpf_bprintf_prepare(char *fmt, u32 fmt_size, const u64 *raw_args,
> +int bpf_bprintf_prepare(const char *fmt, u32 fmt_size, const u64 *raw_args,
>                         u32 num_args, struct bpf_bprintf_data *data)
>  {
>         bool get_buffers = (data->get_bin_args && num_args) || data->get_buf;
> @@ -835,7 +831,7 @@ int bpf_bprintf_prepare(char *fmt, u32 fmt_size, const u64 *raw_args,
>                 return -EINVAL;
>         fmt_size = fmt_end - fmt;
>
> -       if (get_buffers && try_get_buffers(&buffers))
> +       if (get_buffers && bpf_try_get_buffers(&buffers))
>                 return -EBUSY;
>
>         if (data->get_bin_args) {
> --
> 2.47.1
>





[Index of Archives]     [Linux Samsung SoC]     [Linux Rockchip SoC]     [Linux Actions SoC]     [Linux for Synopsys ARC Processors]     [Linux NFS]     [Linux NILFS]     [Linux USB Devel]     [Video for Linux]     [Linux Audio Users]     [Yosemite News]     [Linux Kernel]     [Linux SCSI]


  Powered by Linux