Skip to content

Commit 0426729

Browse files
kkdwivediAlexei Starovoitov
authored andcommitted
bpf: Refactor bprintf buffer support
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. Reviewed-by: Emil Tsalapatis <[email protected]> Signed-off-by: Kumar Kartikeya Dwivedi <[email protected]> Link: https://lore.kernel.org/r/[email protected] Signed-off-by: Alexei Starovoitov <[email protected]>
1 parent da7e9c0 commit 0426729

File tree

2 files changed

+25
-16
lines changed

2 files changed

+25
-16
lines changed

include/linux/bpf.h

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3551,16 +3551,29 @@ bool btf_id_set_contains(const struct btf_id_set *set, u32 id);
35513551
#define MAX_BPRINTF_VARARGS 12
35523552
#define MAX_BPRINTF_BUF 1024
35533553

3554+
/* Per-cpu temp buffers used by printf-like helpers to store the bprintf binary
3555+
* arguments representation.
3556+
*/
3557+
#define MAX_BPRINTF_BIN_ARGS 512
3558+
3559+
struct bpf_bprintf_buffers {
3560+
char bin_args[MAX_BPRINTF_BIN_ARGS];
3561+
char buf[MAX_BPRINTF_BUF];
3562+
};
3563+
35543564
struct bpf_bprintf_data {
35553565
u32 *bin_args;
35563566
char *buf;
35573567
bool get_bin_args;
35583568
bool get_buf;
35593569
};
35603570

3561-
int bpf_bprintf_prepare(char *fmt, u32 fmt_size, const u64 *raw_args,
3571+
int bpf_bprintf_prepare(const char *fmt, u32 fmt_size, const u64 *raw_args,
35623572
u32 num_args, struct bpf_bprintf_data *data);
35633573
void bpf_bprintf_cleanup(struct bpf_bprintf_data *data);
3574+
int bpf_try_get_buffers(struct bpf_bprintf_buffers **bufs);
3575+
void bpf_put_buffers(void);
3576+
35643577

35653578
#ifdef CONFIG_BPF_LSM
35663579
void bpf_cgroup_atype_get(u32 attach_btf_id, int cgroup_atype);

kernel/bpf/helpers.c

Lines changed: 11 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -764,22 +764,13 @@ static int bpf_trace_copy_string(char *buf, void *unsafe_ptr, char fmt_ptype,
764764
return -EINVAL;
765765
}
766766

767-
/* Per-cpu temp buffers used by printf-like helpers to store the bprintf binary
768-
* arguments representation.
769-
*/
770-
#define MAX_BPRINTF_BIN_ARGS 512
771-
772767
/* Support executing three nested bprintf helper calls on a given CPU */
773768
#define MAX_BPRINTF_NEST_LEVEL 3
774-
struct bpf_bprintf_buffers {
775-
char bin_args[MAX_BPRINTF_BIN_ARGS];
776-
char buf[MAX_BPRINTF_BUF];
777-
};
778769

779770
static DEFINE_PER_CPU(struct bpf_bprintf_buffers[MAX_BPRINTF_NEST_LEVEL], bpf_bprintf_bufs);
780771
static DEFINE_PER_CPU(int, bpf_bprintf_nest_level);
781772

782-
static int try_get_buffers(struct bpf_bprintf_buffers **bufs)
773+
int bpf_try_get_buffers(struct bpf_bprintf_buffers **bufs)
783774
{
784775
int nest_level;
785776

@@ -795,16 +786,21 @@ static int try_get_buffers(struct bpf_bprintf_buffers **bufs)
795786
return 0;
796787
}
797788

798-
void bpf_bprintf_cleanup(struct bpf_bprintf_data *data)
789+
void bpf_put_buffers(void)
799790
{
800-
if (!data->bin_args && !data->buf)
801-
return;
802791
if (WARN_ON_ONCE(this_cpu_read(bpf_bprintf_nest_level) == 0))
803792
return;
804793
this_cpu_dec(bpf_bprintf_nest_level);
805794
preempt_enable();
806795
}
807796

797+
void bpf_bprintf_cleanup(struct bpf_bprintf_data *data)
798+
{
799+
if (!data->bin_args && !data->buf)
800+
return;
801+
bpf_put_buffers();
802+
}
803+
808804
/*
809805
* bpf_bprintf_prepare - Generic pass on format strings for bprintf-like helpers
810806
*
@@ -819,7 +815,7 @@ void bpf_bprintf_cleanup(struct bpf_bprintf_data *data)
819815
* In argument preparation mode, if 0 is returned, safe temporary buffers are
820816
* allocated and bpf_bprintf_cleanup should be called to free them after use.
821817
*/
822-
int bpf_bprintf_prepare(char *fmt, u32 fmt_size, const u64 *raw_args,
818+
int bpf_bprintf_prepare(const char *fmt, u32 fmt_size, const u64 *raw_args,
823819
u32 num_args, struct bpf_bprintf_data *data)
824820
{
825821
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,
835831
return -EINVAL;
836832
fmt_size = fmt_end - fmt;
837833

838-
if (get_buffers && try_get_buffers(&buffers))
834+
if (get_buffers && bpf_try_get_buffers(&buffers))
839835
return -EBUSY;
840836

841837
if (data->get_bin_args) {

0 commit comments

Comments
 (0)