From: Alexei Starovoitov <ast-uqk4Ao+rVK5Wk0Htik3J/w@public.gmane.org>
To: "David S. Miller" <davem-fT/PcQaiUtIeIZ0/mPfg9Q@public.gmane.org>
Cc: Ingo Molnar <mingo-DgEjT+Ai2ygdnm+yROfE0A@public.gmane.org>,
Linus Torvalds
<torvalds-de/tnXTf+JLsfHDXvbKv3WD2FQJk+8+b@public.gmane.org>,
Andy Lutomirski <luto-kltTT9wpgjJwATOyAt5JVQ@public.gmane.org>,
Steven Rostedt <rostedt-nx8X9YLhiw1AfugRpC6u6w@public.gmane.org>,
Daniel Borkmann
<dborkman-H+wXaHxf7aLQT0dZR+AlfA@public.gmane.org>,
Chema Gonzalez <chema-hpIqsD4AKlfQT0dZR+AlfA@public.gmane.org>,
Eric Dumazet <edumazet-hpIqsD4AKlfQT0dZR+AlfA@public.gmane.org>,
Peter Zijlstra
<a.p.zijlstra-/NLkJaSkS4VmR6Xm/wNWPw@public.gmane.org>,
Brendan Gregg
<brendan.d.gregg-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org>,
Namhyung Kim <namhyung-DgEjT+Ai2ygdnm+yROfE0A@public.gmane.org>,
"H. Peter Anvin" <hpa-YMNOUZJC4hwAvxtiuMwx3w@public.gmane.org>,
Andrew Morton
<akpm-de/tnXTf+JLsfHDXvbKv3WD2FQJk+8+b@public.gmane.org>,
Kees Cook <keescook-F7+t8E8rja9g9hUCZPvPmw@public.gmane.org>,
linux-api-u79uwXL29TY76Z2rM5mHXA@public.gmane.org,
netdev-u79uwXL29TY76Z2rM5mHXA@public.gmane.org,
linux-kernel-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
Subject: [PATCH RFC v7 net-next 18/28] tracing: allow eBPF programs call printk()
Date: Tue, 26 Aug 2014 19:29:32 -0700 [thread overview]
Message-ID: <1409106582-10095-19-git-send-email-ast@plumgrid.com> (raw)
In-Reply-To: <1409106582-10095-1-git-send-email-ast-uqk4Ao+rVK5Wk0Htik3J/w@public.gmane.org>
limited printk() with %d %u %x %p modifiers only
Signed-off-by: Alexei Starovoitov <ast-uqk4Ao+rVK5Wk0Htik3J/w@public.gmane.org>
---
include/uapi/linux/bpf.h | 1 +
kernel/trace/bpf_trace.c | 61 ++++++++++++++++++++++++++++++++++++++++++++++
2 files changed, 62 insertions(+)
diff --git a/include/uapi/linux/bpf.h b/include/uapi/linux/bpf.h
index 55adff33083e..1ec3d293d14e 100644
--- a/include/uapi/linux/bpf.h
+++ b/include/uapi/linux/bpf.h
@@ -430,6 +430,7 @@ enum bpf_func_id {
BPF_FUNC_fetch_u8, /* u8 bpf_fetch_u8(void *unsafe_ptr) */
BPF_FUNC_memcmp, /* int bpf_memcmp(void *unsafe_ptr, void *safe_ptr, int size) */
BPF_FUNC_dump_stack, /* void bpf_dump_stack(void) */
+ BPF_FUNC_printk, /* int bpf_printk(const char *fmt, int fmt_size, ...) */
__BPF_FUNC_MAX_ID,
};
diff --git a/kernel/trace/bpf_trace.c b/kernel/trace/bpf_trace.c
index b4751e2c0d52..ff98be5a24d6 100644
--- a/kernel/trace/bpf_trace.c
+++ b/kernel/trace/bpf_trace.c
@@ -60,6 +60,60 @@ static u64 bpf_dump_stack(u64 r1, u64 r2, u64 r3, u64 r4, u64 r5)
return 0;
}
+/* limited printk()
+ * only %d %u %x %ld %lu %lx %lld %llu %llx %p conversion specifiers allowed
+ */
+static u64 bpf_printk(u64 r1, u64 fmt_size, u64 r3, u64 r4, u64 r5)
+{
+ char *fmt = (char *) (long) r1;
+ int fmt_cnt = 0;
+ bool mod_l[3] = {};
+ int i;
+
+ /* bpf_check() guarantees that fmt points to bpf program stack and
+ * fmt_size bytes of it were initialized by bpf program
+ */
+ if (fmt[fmt_size - 1] != 0)
+ return -EINVAL;
+
+ /* check format string for allowed specifiers */
+ for (i = 0; i < fmt_size; i++)
+ if (fmt[i] == '%') {
+ if (fmt_cnt >= 3)
+ return -EINVAL;
+ i++;
+ if (i >= fmt_size)
+ return -EINVAL;
+
+ if (fmt[i] == 'l') {
+ mod_l[fmt_cnt] = true;
+ i++;
+ if (i >= fmt_size)
+ return -EINVAL;
+ } else if (fmt[i] == 'p') {
+ mod_l[fmt_cnt] = true;
+ fmt_cnt++;
+ continue;
+ }
+
+ if (fmt[i] == 'l') {
+ mod_l[fmt_cnt] = true;
+ i++;
+ if (i >= fmt_size)
+ return -EINVAL;
+ }
+
+ if (fmt[i] != 'd' && fmt[i] != 'u' && fmt[i] != 'x')
+ return -EINVAL;
+ fmt_cnt++;
+ }
+
+ return __trace_printk((unsigned long) __builtin_return_address(3), fmt,
+ mod_l[0] ? r3 : (u32) r3,
+ mod_l[1] ? r4 : (u32) r4,
+ mod_l[2] ? r5 : (u32) r5);
+}
+
static struct bpf_func_proto tracing_filter_funcs[] = {
#define FETCH(SIZE) \
[BPF_FUNC_fetch_##SIZE] = { \
@@ -86,6 +140,13 @@ static struct bpf_func_proto tracing_filter_funcs[] = {
.gpl_only = false,
.ret_type = RET_VOID,
},
+ [BPF_FUNC_printk] = {
+ .func = bpf_printk,
+ .gpl_only = true,
+ .ret_type = RET_INTEGER,
+ .arg1_type = ARG_PTR_TO_STACK,
+ .arg2_type = ARG_CONST_STACK_SIZE,
+ },
[BPF_FUNC_map_lookup_elem] = {
.func = bpf_map_lookup_elem,
.gpl_only = false,
--
1.7.9.5
WARNING: multiple messages have this Message-ID (diff)
From: Alexei Starovoitov <ast@plumgrid.com>
To: "David S. Miller" <davem@davemloft.net>
Cc: Ingo Molnar <mingo@kernel.org>,
Linus Torvalds <torvalds@linux-foundation.org>,
Andy Lutomirski <luto@amacapital.net>,
Steven Rostedt <rostedt@goodmis.org>,
Daniel Borkmann <dborkman@redhat.com>,
Chema Gonzalez <chema@google.com>,
Eric Dumazet <edumazet@google.com>,
Peter Zijlstra <a.p.zijlstra@chello.nl>,
Brendan Gregg <brendan.d.gregg@gmail.com>,
Namhyung Kim <namhyung@kernel.org>,
"H. Peter Anvin" <hpa@zytor.com>,
Andrew Morton <akpm@linux-foundation.org>,
Kees Cook <keescook@chromium.org>,
linux-api@vger.kernel.org, netdev@vger.kernel.org,
linux-kernel@vger.kernel.org
Subject: [PATCH RFC v7 net-next 18/28] tracing: allow eBPF programs call printk()
Date: Tue, 26 Aug 2014 19:29:32 -0700 [thread overview]
Message-ID: <1409106582-10095-19-git-send-email-ast@plumgrid.com> (raw)
In-Reply-To: <1409106582-10095-1-git-send-email-ast@plumgrid.com>
limited printk() with %d %u %x %p modifiers only
Signed-off-by: Alexei Starovoitov <ast@plumgrid.com>
---
include/uapi/linux/bpf.h | 1 +
kernel/trace/bpf_trace.c | 61 ++++++++++++++++++++++++++++++++++++++++++++++
2 files changed, 62 insertions(+)
diff --git a/include/uapi/linux/bpf.h b/include/uapi/linux/bpf.h
index 55adff33083e..1ec3d293d14e 100644
--- a/include/uapi/linux/bpf.h
+++ b/include/uapi/linux/bpf.h
@@ -430,6 +430,7 @@ enum bpf_func_id {
BPF_FUNC_fetch_u8, /* u8 bpf_fetch_u8(void *unsafe_ptr) */
BPF_FUNC_memcmp, /* int bpf_memcmp(void *unsafe_ptr, void *safe_ptr, int size) */
BPF_FUNC_dump_stack, /* void bpf_dump_stack(void) */
+ BPF_FUNC_printk, /* int bpf_printk(const char *fmt, int fmt_size, ...) */
__BPF_FUNC_MAX_ID,
};
diff --git a/kernel/trace/bpf_trace.c b/kernel/trace/bpf_trace.c
index b4751e2c0d52..ff98be5a24d6 100644
--- a/kernel/trace/bpf_trace.c
+++ b/kernel/trace/bpf_trace.c
@@ -60,6 +60,60 @@ static u64 bpf_dump_stack(u64 r1, u64 r2, u64 r3, u64 r4, u64 r5)
return 0;
}
+/* limited printk()
+ * only %d %u %x %ld %lu %lx %lld %llu %llx %p conversion specifiers allowed
+ */
+static u64 bpf_printk(u64 r1, u64 fmt_size, u64 r3, u64 r4, u64 r5)
+{
+ char *fmt = (char *) (long) r1;
+ int fmt_cnt = 0;
+ bool mod_l[3] = {};
+ int i;
+
+ /* bpf_check() guarantees that fmt points to bpf program stack and
+ * fmt_size bytes of it were initialized by bpf program
+ */
+ if (fmt[fmt_size - 1] != 0)
+ return -EINVAL;
+
+ /* check format string for allowed specifiers */
+ for (i = 0; i < fmt_size; i++)
+ if (fmt[i] == '%') {
+ if (fmt_cnt >= 3)
+ return -EINVAL;
+ i++;
+ if (i >= fmt_size)
+ return -EINVAL;
+
+ if (fmt[i] == 'l') {
+ mod_l[fmt_cnt] = true;
+ i++;
+ if (i >= fmt_size)
+ return -EINVAL;
+ } else if (fmt[i] == 'p') {
+ mod_l[fmt_cnt] = true;
+ fmt_cnt++;
+ continue;
+ }
+
+ if (fmt[i] == 'l') {
+ mod_l[fmt_cnt] = true;
+ i++;
+ if (i >= fmt_size)
+ return -EINVAL;
+ }
+
+ if (fmt[i] != 'd' && fmt[i] != 'u' && fmt[i] != 'x')
+ return -EINVAL;
+ fmt_cnt++;
+ }
+
+ return __trace_printk((unsigned long) __builtin_return_address(3), fmt,
+ mod_l[0] ? r3 : (u32) r3,
+ mod_l[1] ? r4 : (u32) r4,
+ mod_l[2] ? r5 : (u32) r5);
+}
+
static struct bpf_func_proto tracing_filter_funcs[] = {
#define FETCH(SIZE) \
[BPF_FUNC_fetch_##SIZE] = { \
@@ -86,6 +140,13 @@ static struct bpf_func_proto tracing_filter_funcs[] = {
.gpl_only = false,
.ret_type = RET_VOID,
},
+ [BPF_FUNC_printk] = {
+ .func = bpf_printk,
+ .gpl_only = true,
+ .ret_type = RET_INTEGER,
+ .arg1_type = ARG_PTR_TO_STACK,
+ .arg2_type = ARG_CONST_STACK_SIZE,
+ },
[BPF_FUNC_map_lookup_elem] = {
.func = bpf_map_lookup_elem,
.gpl_only = false,
--
1.7.9.5
next prev parent reply other threads:[~2014-08-27 2:29 UTC|newest]
Thread overview: 51+ messages / expand[flat|nested] mbox.gz Atom feed top
2014-08-27 2:29 [PATCH RFC v7 net-next 00/28] BPF syscall Alexei Starovoitov
2014-08-27 2:29 ` Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 01/28] net: filter: add "load 64-bit immediate" eBPF instruction Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 02/28] net: filter: split filter.h and expose eBPF to user space Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 03/28] bpf: introduce syscall(BPF, ...) and BPF maps Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 04/28] bpf: enable bpf syscall on x64 and i386 Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 05/28] bpf: add lookup/update/delete/iterate methods to BPF maps Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 06/28] bpf: add hashtable type of " Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 07/28] bpf: expand BPF syscall with program load/unload Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 08/28] bpf: handle pseudo BPF_CALL insn Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 09/28] bpf: verifier (add docs) Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 10/28] bpf: verifier (add ability to receive verification log) Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 11/28] bpf: handle pseudo BPF_LD_IMM64 insn Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 12/28] bpf: verifier (add branch/goto checks) Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 13/28] bpf: verifier (add verifier core) Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 14/28] bpf: verifier (add state prunning optimization) Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 17/28] tracing: allow eBPF programs to be attached to events Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 19/28] tracing: allow eBPF programs to be attached to kprobe/kretprobe Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 20/28] tracing: allow eBPF programs to call ktime_get_ns() and get_current() Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 21/28] samples: bpf: add mini eBPF library to manipulate maps and programs Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 22/28] samples: bpf: example of tracing filters with eBPF Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 23/28] bpf: verifier test Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 26/28] samples: bpf: eBPF example in C Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 27/28] samples: bpf: counting " Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 28/28] samples: bpf: IO latency analysis (iosnoop/heatmap) Alexei Starovoitov
2014-08-27 3:56 ` [PATCH RFC v7 net-next 00/28] BPF syscall Andy Lutomirski
2014-08-27 4:35 ` Alexei Starovoitov
2014-08-27 4:49 ` Andy Lutomirski
2014-08-27 4:57 ` Alexei Starovoitov
[not found] ` <CAMEtUuw1n1HzAeyKFj9=nGq7RKZq7TADS-6M_BkHbTsWJ_Gm-Q-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>
2014-08-27 18:26 ` Andy Lutomirski
2014-08-27 18:26 ` Andy Lutomirski
[not found] ` <CALCETrXAfZJTsF2nPFw55rHkfbNXKQuF8Frnq3e1wHEoGxLM4w-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>
2014-08-27 19:18 ` Stephen Hemminger
2014-08-27 19:18 ` Stephen Hemminger
2014-08-27 19:35 ` Daniel Borkmann
2014-08-27 19:35 ` Daniel Borkmann
2014-08-27 19:37 ` Alexei Starovoitov
2014-08-27 19:37 ` Alexei Starovoitov
[not found] ` <1409106582-10095-1-git-send-email-ast-uqk4Ao+rVK5Wk0Htik3J/w@public.gmane.org>
2014-08-27 2:29 ` [PATCH RFC v7 net-next 15/28] bpf: allow eBPF programs to use maps Alexei Starovoitov
2014-08-27 2:29 ` Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 16/28] bpf: split eBPF out of NET Alexei Starovoitov
2014-08-27 2:29 ` Alexei Starovoitov
2014-08-27 2:29 ` Alexei Starovoitov [this message]
2014-08-27 2:29 ` [PATCH RFC v7 net-next 18/28] tracing: allow eBPF programs call printk() Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 24/28] bpf: llvm backend Alexei Starovoitov
2014-08-27 2:29 ` Alexei Starovoitov
2014-08-27 2:29 ` [PATCH RFC v7 net-next 25/28] samples: bpf: elf file loader Alexei Starovoitov
2014-08-27 2:29 ` Alexei Starovoitov
2014-08-27 6:11 ` [PATCH RFC v7 net-next 00/28] BPF syscall David Miller
2014-08-27 6:11 ` David Miller
[not found] ` <20140826.231155.421325307812864648.davem-fT/PcQaiUtIeIZ0/mPfg9Q@public.gmane.org>
2014-08-27 18:24 ` Steven Stewart-Gallus
2014-08-27 18:24 ` Steven Stewart-Gallus
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=1409106582-10095-19-git-send-email-ast@plumgrid.com \
--to=ast-uqk4ao+rvk5wk0htik3j/w@public.gmane.org \
--cc=a.p.zijlstra-/NLkJaSkS4VmR6Xm/wNWPw@public.gmane.org \
--cc=akpm-de/tnXTf+JLsfHDXvbKv3WD2FQJk+8+b@public.gmane.org \
--cc=brendan.d.gregg-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org \
--cc=chema-hpIqsD4AKlfQT0dZR+AlfA@public.gmane.org \
--cc=davem-fT/PcQaiUtIeIZ0/mPfg9Q@public.gmane.org \
--cc=dborkman-H+wXaHxf7aLQT0dZR+AlfA@public.gmane.org \
--cc=edumazet-hpIqsD4AKlfQT0dZR+AlfA@public.gmane.org \
--cc=hpa-YMNOUZJC4hwAvxtiuMwx3w@public.gmane.org \
--cc=keescook-F7+t8E8rja9g9hUCZPvPmw@public.gmane.org \
--cc=linux-api-u79uwXL29TY76Z2rM5mHXA@public.gmane.org \
--cc=linux-kernel-u79uwXL29TY76Z2rM5mHXA@public.gmane.org \
--cc=luto-kltTT9wpgjJwATOyAt5JVQ@public.gmane.org \
--cc=mingo-DgEjT+Ai2ygdnm+yROfE0A@public.gmane.org \
--cc=namhyung-DgEjT+Ai2ygdnm+yROfE0A@public.gmane.org \
--cc=netdev-u79uwXL29TY76Z2rM5mHXA@public.gmane.org \
--cc=rostedt-nx8X9YLhiw1AfugRpC6u6w@public.gmane.org \
--cc=torvalds-de/tnXTf+JLsfHDXvbKv3WD2FQJk+8+b@public.gmane.org \
/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.