All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH v2 bpf-next 0/5] switch samples and tests to libbpf perf buffer API
@ 2019-07-23 21:34 Andrii Nakryiko
  2019-07-23 21:34 ` [PATCH v2 bpf-next 1/5] selftests/bpf: convert test_get_stack_raw_tp to perf_buffer API Andrii Nakryiko
                   ` (5 more replies)
  0 siblings, 6 replies; 8+ messages in thread
From: Andrii Nakryiko @ 2019-07-23 21:34 UTC (permalink / raw)
  To: bpf, netdev, ast, daniel, songliubraving
  Cc: andrii.nakryiko, kernel-team, Andrii Nakryiko

There were few more tests and samples that were using custom perf buffer setup
code from trace_helpers.h. This patch set gets rid of all the usages of those
and removes helpers themselves. Libbpf provides nicer, but equally powerful
set of APIs to work with perf ring buffers, so let's have all the samples use

v1->v2:
- make logging message one long line instead of two (Song).

Andrii Nakryiko (5):
  selftests/bpf: convert test_get_stack_raw_tp to perf_buffer API
  selftests/bpf: switch test_tcpnotify to perf_buffer API
  samples/bpf: convert xdp_sample_pkts_user to perf_buffer API
  samples/bpf: switch trace_output sample to perf_buffer API
  selftests/bpf: remove perf buffer helpers

 samples/bpf/trace_output_user.c               |  43 ++----
 samples/bpf/xdp_sample_pkts_user.c            |  61 +++------
 .../bpf/prog_tests/get_stack_raw_tp.c         |  78 ++++++-----
 .../bpf/progs/test_get_stack_rawtp.c          |   2 +-
 .../selftests/bpf/test_tcpnotify_user.c       |  90 +++++--------
 tools/testing/selftests/bpf/trace_helpers.c   | 125 ------------------
 tools/testing/selftests/bpf/trace_helpers.h   |   9 --
 7 files changed, 111 insertions(+), 297 deletions(-)

-- 
2.17.1


^ permalink raw reply	[flat|nested] 8+ messages in thread

* [PATCH v2 bpf-next 1/5] selftests/bpf: convert test_get_stack_raw_tp to perf_buffer API
  2019-07-23 21:34 [PATCH v2 bpf-next 0/5] switch samples and tests to libbpf perf buffer API Andrii Nakryiko
@ 2019-07-23 21:34 ` Andrii Nakryiko
  2019-07-23 22:02   ` Song Liu
  2019-07-23 21:34 ` [PATCH v2 bpf-next 2/5] selftests/bpf: switch test_tcpnotify " Andrii Nakryiko
                   ` (4 subsequent siblings)
  5 siblings, 1 reply; 8+ messages in thread
From: Andrii Nakryiko @ 2019-07-23 21:34 UTC (permalink / raw)
  To: bpf, netdev, ast, daniel, songliubraving
  Cc: andrii.nakryiko, kernel-team, Andrii Nakryiko

Convert test_get_stack_raw_tp test to new perf_buffer API.

Signed-off-by: Andrii Nakryiko <andriin@fb.com>
---
 .../bpf/prog_tests/get_stack_raw_tp.c         | 78 ++++++++++---------
 .../bpf/progs/test_get_stack_rawtp.c          |  2 +-
 2 files changed, 44 insertions(+), 36 deletions(-)

diff --git a/tools/testing/selftests/bpf/prog_tests/get_stack_raw_tp.c b/tools/testing/selftests/bpf/prog_tests/get_stack_raw_tp.c
index c2a0a9d5591b..9d73a8f932ac 100644
--- a/tools/testing/selftests/bpf/prog_tests/get_stack_raw_tp.c
+++ b/tools/testing/selftests/bpf/prog_tests/get_stack_raw_tp.c
@@ -1,8 +1,15 @@
 // SPDX-License-Identifier: GPL-2.0
+#define _GNU_SOURCE
+#include <pthread.h>
+#include <sched.h>
+#include <sys/socket.h>
 #include <test_progs.h>
 
 #define MAX_CNT_RAWTP	10ull
 #define MAX_STACK_RAWTP	100
+
+static int duration = 0;
+
 struct get_stack_trace_t {
 	int pid;
 	int kern_stack_size;
@@ -13,7 +20,7 @@ struct get_stack_trace_t {
 	struct bpf_stack_build_id user_stack_buildid[MAX_STACK_RAWTP];
 };
 
-static int get_stack_print_output(void *data, int size)
+static void get_stack_print_output(void *ctx, int cpu, void *data, __u32 size)
 {
 	bool good_kern_stack = false, good_user_stack = false;
 	const char *nonjit_func = "___bpf_prog_run";
@@ -65,75 +72,76 @@ static int get_stack_print_output(void *data, int size)
 		if (e->user_stack_size > 0 && e->user_stack_buildid_size > 0)
 			good_user_stack = true;
 	}
-	if (!good_kern_stack || !good_user_stack)
-		return LIBBPF_PERF_EVENT_ERROR;
 
-	if (cnt == MAX_CNT_RAWTP)
-		return LIBBPF_PERF_EVENT_DONE;
-
-	return LIBBPF_PERF_EVENT_CONT;
+	if (!good_kern_stack)
+	    CHECK(!good_kern_stack, "kern_stack", "corrupted kernel stack\n");
+	if (!good_user_stack)
+	    CHECK(!good_user_stack, "user_stack", "corrupted user stack\n");
 }
 
 void test_get_stack_raw_tp(void)
 {
 	const char *file = "./test_get_stack_rawtp.o";
-	int i, efd, err, prog_fd, pmu_fd, perfmap_fd;
-	struct perf_event_attr attr = {};
+	const char *prog_name = "raw_tracepoint/sys_enter";
+	int i, err, prog_fd, exp_cnt = MAX_CNT_RAWTP;
+	struct perf_buffer_opts pb_opts = {};
+	struct perf_buffer *pb = NULL;
+	struct bpf_link *link = NULL;
 	struct timespec tv = {0, 10};
-	__u32 key = 0, duration = 0;
+	struct bpf_program *prog;
 	struct bpf_object *obj;
+	struct bpf_map *map;
+	cpu_set_t cpu_set;
 
 	err = bpf_prog_load(file, BPF_PROG_TYPE_RAW_TRACEPOINT, &obj, &prog_fd);
 	if (CHECK(err, "prog_load raw tp", "err %d errno %d\n", err, errno))
 		return;
 
-	efd = bpf_raw_tracepoint_open("sys_enter", prog_fd);
-	if (CHECK(efd < 0, "raw_tp_open", "err %d errno %d\n", efd, errno))
+	prog = bpf_object__find_program_by_title(obj, prog_name);
+	if (CHECK(!prog, "find_probe", "prog '%s' not found\n", prog_name))
 		goto close_prog;
 
-	perfmap_fd = bpf_find_map(__func__, obj, "perfmap");
-	if (CHECK(perfmap_fd < 0, "bpf_find_map", "err %d errno %d\n",
-		  perfmap_fd, errno))
+	map = bpf_object__find_map_by_name(obj, "perfmap");
+	if (CHECK(!map, "bpf_find_map", "not found\n"))
 		goto close_prog;
 
 	err = load_kallsyms();
 	if (CHECK(err < 0, "load_kallsyms", "err %d errno %d\n", err, errno))
 		goto close_prog;
 
-	attr.sample_type = PERF_SAMPLE_RAW;
-	attr.type = PERF_TYPE_SOFTWARE;
-	attr.config = PERF_COUNT_SW_BPF_OUTPUT;
-	pmu_fd = syscall(__NR_perf_event_open, &attr, getpid()/*pid*/, -1/*cpu*/,
-			 -1/*group_fd*/, 0);
-	if (CHECK(pmu_fd < 0, "perf_event_open", "err %d errno %d\n", pmu_fd,
-		  errno))
+	CPU_ZERO(&cpu_set);
+	CPU_SET(0, &cpu_set);
+	err = pthread_setaffinity_np(pthread_self(), sizeof(cpu_set), &cpu_set);
+	if (CHECK(err, "set_affinity", "err %d, errno %d\n", err, errno))
 		goto close_prog;
 
-	err = bpf_map_update_elem(perfmap_fd, &key, &pmu_fd, BPF_ANY);
-	if (CHECK(err < 0, "bpf_map_update_elem", "err %d errno %d\n", err,
-		  errno))
+	link = bpf_program__attach_raw_tracepoint(prog, "sys_enter");
+	if (CHECK(IS_ERR(link), "attach_raw_tp", "err %ld\n", PTR_ERR(link)))
 		goto close_prog;
 
-	err = ioctl(pmu_fd, PERF_EVENT_IOC_ENABLE, 0);
-	if (CHECK(err < 0, "ioctl PERF_EVENT_IOC_ENABLE", "err %d errno %d\n",
-		  err, errno))
-		goto close_prog;
-
-	err = perf_event_mmap(pmu_fd);
-	if (CHECK(err < 0, "perf_event_mmap", "err %d errno %d\n", err, errno))
+	pb_opts.sample_cb = get_stack_print_output;
+	pb = perf_buffer__new(bpf_map__fd(map), 8, &pb_opts);
+	if (CHECK(IS_ERR(pb), "perf_buf__new", "err %ld\n", PTR_ERR(pb)))
 		goto close_prog;
 
 	/* trigger some syscall action */
 	for (i = 0; i < MAX_CNT_RAWTP; i++)
 		nanosleep(&tv, NULL);
 
-	err = perf_event_poller(pmu_fd, get_stack_print_output);
-	if (CHECK(err < 0, "perf_event_poller", "err %d errno %d\n", err, errno))
-		goto close_prog;
+	while (exp_cnt > 0) {
+		err = perf_buffer__poll(pb, 100);
+		if (err < 0 && CHECK(err < 0, "pb__poll", "err %d\n", err))
+			goto close_prog;
+		exp_cnt -= err;
+	}
 
 	goto close_prog_noerr;
 close_prog:
 	error_cnt++;
 close_prog_noerr:
+	if (!IS_ERR_OR_NULL(link))
+		bpf_link__destroy(link);
+	if (!IS_ERR_OR_NULL(pb))
+		perf_buffer__free(pb);
 	bpf_object__close(obj);
 }
diff --git a/tools/testing/selftests/bpf/progs/test_get_stack_rawtp.c b/tools/testing/selftests/bpf/progs/test_get_stack_rawtp.c
index 33254b771384..f8ffa3f3d44b 100644
--- a/tools/testing/selftests/bpf/progs/test_get_stack_rawtp.c
+++ b/tools/testing/selftests/bpf/progs/test_get_stack_rawtp.c
@@ -55,7 +55,7 @@ struct {
 	__type(value, raw_stack_trace_t);
 } rawdata_map SEC(".maps");
 
-SEC("tracepoint/raw_syscalls/sys_enter")
+SEC("raw_tracepoint/sys_enter")
 int bpf_prog1(void *ctx)
 {
 	int max_len, max_buildid_len, usize, ksize, total_size;
-- 
2.17.1


^ permalink raw reply related	[flat|nested] 8+ messages in thread

* [PATCH v2 bpf-next 2/5] selftests/bpf: switch test_tcpnotify to perf_buffer API
  2019-07-23 21:34 [PATCH v2 bpf-next 0/5] switch samples and tests to libbpf perf buffer API Andrii Nakryiko
  2019-07-23 21:34 ` [PATCH v2 bpf-next 1/5] selftests/bpf: convert test_get_stack_raw_tp to perf_buffer API Andrii Nakryiko
@ 2019-07-23 21:34 ` Andrii Nakryiko
  2019-07-23 21:34 ` [PATCH v2 bpf-next 3/5] samples/bpf: convert xdp_sample_pkts_user " Andrii Nakryiko
                   ` (3 subsequent siblings)
  5 siblings, 0 replies; 8+ messages in thread
From: Andrii Nakryiko @ 2019-07-23 21:34 UTC (permalink / raw)
  To: bpf, netdev, ast, daniel, songliubraving
  Cc: andrii.nakryiko, kernel-team, Andrii Nakryiko

Switch test_tcpnotify test to use libbpf's perf_buffer API instead of
re-implementing portion of it.

Signed-off-by: Andrii Nakryiko <andriin@fb.com>
Acked-by: Song Liu <songliubraving@fb.com>
---
 .../selftests/bpf/test_tcpnotify_user.c       | 90 ++++++++-----------
 1 file changed, 36 insertions(+), 54 deletions(-)

diff --git a/tools/testing/selftests/bpf/test_tcpnotify_user.c b/tools/testing/selftests/bpf/test_tcpnotify_user.c
index 86152d9ae95b..f9765ddf0761 100644
--- a/tools/testing/selftests/bpf/test_tcpnotify_user.c
+++ b/tools/testing/selftests/bpf/test_tcpnotify_user.c
@@ -17,6 +17,7 @@
 #include <linux/rtnetlink.h>
 #include <signal.h>
 #include <linux/perf_event.h>
+#include <linux/err.h>
 
 #include "bpf_rlimit.h"
 #include "bpf_util.h"
@@ -30,28 +31,34 @@
 pthread_t tid;
 int rx_callbacks;
 
-static int dummyfn(void *data, int size)
+static void dummyfn(void *ctx, int cpu, void *data, __u32 size)
 {
 	struct tcp_notifier *t = data;
 
 	if (t->type != 0xde || t->subtype != 0xad ||
 	    t->source != 0xbe || t->hash != 0xef)
-		return 1;
+		return;
 	rx_callbacks++;
-	return 0;
 }
 
-void tcp_notifier_poller(int fd)
+void tcp_notifier_poller(struct perf_buffer *pb)
 {
-	while (1)
-		perf_event_poller(fd, dummyfn);
+	int err;
+
+	while (1) {
+		err = perf_buffer__poll(pb, 100);
+		if (err < 0 && err != -EINTR) {
+			printf("failed perf_buffer__poll: %d\n", err);
+			return;
+		}
+	}
 }
 
 static void *poller_thread(void *arg)
 {
-	int fd = *(int *)arg;
+	struct perf_buffer *pb = arg;
 
-	tcp_notifier_poller(fd);
+	tcp_notifier_poller(pb);
 	return arg;
 }
 
@@ -60,52 +67,20 @@ int verify_result(const struct tcpnotify_globals *result)
 	return (result->ncalls > 0 && result->ncalls == rx_callbacks ? 0 : 1);
 }
 
-static int bpf_find_map(const char *test, struct bpf_object *obj,
-			const char *name)
-{
-	struct bpf_map *map;
-
-	map = bpf_object__find_map_by_name(obj, name);
-	if (!map) {
-		printf("%s:FAIL:map '%s' not found\n", test, name);
-		return -1;
-	}
-	return bpf_map__fd(map);
-}
-
-static int setup_bpf_perf_event(int mapfd)
-{
-	struct perf_event_attr attr = {
-		.sample_type = PERF_SAMPLE_RAW,
-		.type = PERF_TYPE_SOFTWARE,
-		.config = PERF_COUNT_SW_BPF_OUTPUT,
-	};
-	int key = 0;
-	int pmu_fd;
-
-	pmu_fd = syscall(__NR_perf_event_open, &attr, -1, 0, -1, 0);
-	if (pmu_fd < 0)
-		return pmu_fd;
-	bpf_map_update_elem(mapfd, &key, &pmu_fd, BPF_ANY);
-
-	ioctl(pmu_fd, PERF_EVENT_IOC_ENABLE, 0);
-	return pmu_fd;
-}
-
 int main(int argc, char **argv)
 {
 	const char *file = "test_tcpnotify_kern.o";
-	int prog_fd, map_fd, perf_event_fd;
+	struct bpf_map *perf_map, *global_map;
+	struct perf_buffer_opts pb_opts = {};
 	struct tcpnotify_globals g = {0};
+	struct perf_buffer *pb = NULL;
 	const char *cg_path = "/foo";
+	int prog_fd, rv, cg_fd = -1;
 	int error = EXIT_FAILURE;
 	struct bpf_object *obj;
-	int cg_fd = -1;
-	__u32 key = 0;
-	int rv;
 	char test_script[80];
-	int pmu_fd;
 	cpu_set_t cpuset;
+	__u32 key = 0;
 
 	CPU_ZERO(&cpuset);
 	CPU_SET(0, &cpuset);
@@ -133,19 +108,24 @@ int main(int argc, char **argv)
 		goto err;
 	}
 
-	perf_event_fd = bpf_find_map(__func__, obj, "perf_event_map");
-	if (perf_event_fd < 0)
+	perf_map = bpf_object__find_map_by_name(obj, "perf_event_map");
+	if (!perf_map) {
+		printf("FAIL:map '%s' not found\n", "perf_event_map");
 		goto err;
+	}
 
-	map_fd = bpf_find_map(__func__, obj, "global_map");
-	if (map_fd < 0)
-		goto err;
+	global_map = bpf_object__find_map_by_name(obj, "global_map");
+	if (!global_map) {
+		printf("FAIL:map '%s' not found\n", "global_map");
+		return -1;
+	}
 
-	pmu_fd = setup_bpf_perf_event(perf_event_fd);
-	if (pmu_fd < 0 || perf_event_mmap(pmu_fd) < 0)
+	pb_opts.sample_cb = dummyfn;
+	pb = perf_buffer__new(bpf_map__fd(perf_map), 8, &pb_opts);
+	if (IS_ERR(pb))
 		goto err;
 
-	pthread_create(&tid, NULL, poller_thread, (void *)&pmu_fd);
+	pthread_create(&tid, NULL, poller_thread, pb);
 
 	sprintf(test_script,
 		"iptables -A INPUT -p tcp --dport %d -j DROP",
@@ -162,7 +142,7 @@ int main(int argc, char **argv)
 		TESTPORT);
 	system(test_script);
 
-	rv = bpf_map_lookup_elem(map_fd, &key, &g);
+	rv = bpf_map_lookup_elem(bpf_map__fd(global_map), &key, &g);
 	if (rv != 0) {
 		printf("FAILED: bpf_map_lookup_elem returns %d\n", rv);
 		goto err;
@@ -182,5 +162,7 @@ int main(int argc, char **argv)
 	bpf_prog_detach(cg_fd, BPF_CGROUP_SOCK_OPS);
 	close(cg_fd);
 	cleanup_cgroup_environment();
+	if (!IS_ERR_OR_NULL(pb))
+		perf_buffer__free(pb);
 	return error;
 }
-- 
2.17.1


^ permalink raw reply related	[flat|nested] 8+ messages in thread

* [PATCH v2 bpf-next 3/5] samples/bpf: convert xdp_sample_pkts_user to perf_buffer API
  2019-07-23 21:34 [PATCH v2 bpf-next 0/5] switch samples and tests to libbpf perf buffer API Andrii Nakryiko
  2019-07-23 21:34 ` [PATCH v2 bpf-next 1/5] selftests/bpf: convert test_get_stack_raw_tp to perf_buffer API Andrii Nakryiko
  2019-07-23 21:34 ` [PATCH v2 bpf-next 2/5] selftests/bpf: switch test_tcpnotify " Andrii Nakryiko
@ 2019-07-23 21:34 ` Andrii Nakryiko
  2019-07-23 21:34 ` [PATCH v2 bpf-next 4/5] samples/bpf: switch trace_output sample " Andrii Nakryiko
                   ` (2 subsequent siblings)
  5 siblings, 0 replies; 8+ messages in thread
From: Andrii Nakryiko @ 2019-07-23 21:34 UTC (permalink / raw)
  To: bpf, netdev, ast, daniel, songliubraving
  Cc: andrii.nakryiko, kernel-team, Andrii Nakryiko

Convert xdp_sample_pkts_user to libbpf's perf_buffer API.

Signed-off-by: Andrii Nakryiko <andriin@fb.com>
Acked-by: Song Liu <songliubraving@fb.com>
Acked-by: Toke Høiland-Jørgensen <toke@redhat.com>
---
 samples/bpf/xdp_sample_pkts_user.c | 61 +++++++++---------------------
 1 file changed, 17 insertions(+), 44 deletions(-)

diff --git a/samples/bpf/xdp_sample_pkts_user.c b/samples/bpf/xdp_sample_pkts_user.c
index dc66345a929a..3002714e3cd5 100644
--- a/samples/bpf/xdp_sample_pkts_user.c
+++ b/samples/bpf/xdp_sample_pkts_user.c
@@ -17,14 +17,13 @@
 #include <linux/if_link.h>
 
 #include "perf-sys.h"
-#include "trace_helpers.h"
 
 #define MAX_CPUS 128
-static int pmu_fds[MAX_CPUS], if_idx;
-static struct perf_event_mmap_page *headers[MAX_CPUS];
+static int if_idx;
 static char *if_name;
 static __u32 xdp_flags = XDP_FLAGS_UPDATE_IF_NOEXIST;
 static __u32 prog_id;
+static struct perf_buffer *pb = NULL;
 
 static int do_attach(int idx, int fd, const char *name)
 {
@@ -73,7 +72,7 @@ static int do_detach(int idx, const char *name)
 
 #define SAMPLE_SIZE 64
 
-static int print_bpf_output(void *data, int size)
+static void print_bpf_output(void *ctx, int cpu, void *data, __u32 size)
 {
 	struct {
 		__u16 cookie;
@@ -83,45 +82,20 @@ static int print_bpf_output(void *data, int size)
 	int i;
 
 	if (e->cookie != 0xdead) {
-		printf("BUG cookie %x sized %d\n",
-		       e->cookie, size);
-		return LIBBPF_PERF_EVENT_ERROR;
+		printf("BUG cookie %x sized %d\n", e->cookie, size);
+		return;
 	}
 
 	printf("Pkt len: %-5d bytes. Ethernet hdr: ", e->pkt_len);
 	for (i = 0; i < 14 && i < e->pkt_len; i++)
 		printf("%02x ", e->pkt_data[i]);
 	printf("\n");
-
-	return LIBBPF_PERF_EVENT_CONT;
-}
-
-static void test_bpf_perf_event(int map_fd, int num)
-{
-	struct perf_event_attr attr = {
-		.sample_type = PERF_SAMPLE_RAW,
-		.type = PERF_TYPE_SOFTWARE,
-		.config = PERF_COUNT_SW_BPF_OUTPUT,
-		.wakeup_events = 1, /* get an fd notification for every event */
-	};
-	int i;
-
-	for (i = 0; i < num; i++) {
-		int key = i;
-
-		pmu_fds[i] = sys_perf_event_open(&attr, -1/*pid*/, i/*cpu*/,
-						 -1/*group_fd*/, 0);
-
-		assert(pmu_fds[i] >= 0);
-		assert(bpf_map_update_elem(map_fd, &key,
-					   &pmu_fds[i], BPF_ANY) == 0);
-		ioctl(pmu_fds[i], PERF_EVENT_IOC_ENABLE, 0);
-	}
 }
 
 static void sig_handler(int signo)
 {
 	do_detach(if_idx, if_name);
+	perf_buffer__free(pb);
 	exit(0);
 }
 
@@ -140,13 +114,13 @@ int main(int argc, char **argv)
 	struct bpf_prog_load_attr prog_load_attr = {
 		.prog_type	= BPF_PROG_TYPE_XDP,
 	};
+	struct perf_buffer_opts pb_opts = {};
 	const char *optstr = "F";
 	int prog_fd, map_fd, opt;
 	struct bpf_object *obj;
 	struct bpf_map *map;
 	char filename[256];
-	int ret, err, i;
-	int numcpus;
+	int ret, err;
 
 	while ((opt = getopt(argc, argv, optstr)) != -1) {
 		switch (opt) {
@@ -169,10 +143,6 @@ int main(int argc, char **argv)
 		return 1;
 	}
 
-	numcpus = get_nprocs();
-	if (numcpus > MAX_CPUS)
-		numcpus = MAX_CPUS;
-
 	snprintf(filename, sizeof(filename), "%s_kern.o", argv[0]);
 	prog_load_attr.file = filename;
 
@@ -211,14 +181,17 @@ int main(int argc, char **argv)
 		return 1;
 	}
 
-	test_bpf_perf_event(map_fd, numcpus);
+	pb_opts.sample_cb = print_bpf_output;
+	pb = perf_buffer__new(map_fd, 8, &pb_opts);
+	err = libbpf_get_error(pb);
+	if (err) {
+		perror("perf_buffer setup failed");
+		return 1;
+	}
 
-	for (i = 0; i < numcpus; i++)
-		if (perf_event_mmap_header(pmu_fds[i], &headers[i]) < 0)
-			return 1;
+	while ((ret = perf_buffer__poll(pb, 1000)) >= 0) {
+	}
 
-	ret = perf_event_poller_multi(pmu_fds, headers, numcpus,
-				      print_bpf_output);
 	kill(0, SIGINT);
 	return ret;
 }
-- 
2.17.1


^ permalink raw reply related	[flat|nested] 8+ messages in thread

* [PATCH v2 bpf-next 4/5] samples/bpf: switch trace_output sample to perf_buffer API
  2019-07-23 21:34 [PATCH v2 bpf-next 0/5] switch samples and tests to libbpf perf buffer API Andrii Nakryiko
                   ` (2 preceding siblings ...)
  2019-07-23 21:34 ` [PATCH v2 bpf-next 3/5] samples/bpf: convert xdp_sample_pkts_user " Andrii Nakryiko
@ 2019-07-23 21:34 ` Andrii Nakryiko
  2019-07-23 21:34 ` [PATCH v2 bpf-next 5/5] selftests/bpf: remove perf buffer helpers Andrii Nakryiko
  2019-07-23 23:09 ` [PATCH v2 bpf-next 0/5] switch samples and tests to libbpf perf buffer API Alexei Starovoitov
  5 siblings, 0 replies; 8+ messages in thread
From: Andrii Nakryiko @ 2019-07-23 21:34 UTC (permalink / raw)
  To: bpf, netdev, ast, daniel, songliubraving
  Cc: andrii.nakryiko, kernel-team, Andrii Nakryiko

Convert trace_output sample to libbpf's perf_buffer API.

Signed-off-by: Andrii Nakryiko <andriin@fb.com>
Acked-by: Song Liu <songliubraving@fb.com>
---
 samples/bpf/trace_output_user.c | 43 +++++++++++----------------------
 1 file changed, 14 insertions(+), 29 deletions(-)

diff --git a/samples/bpf/trace_output_user.c b/samples/bpf/trace_output_user.c
index 2dd1d39b152a..8ee47699a870 100644
--- a/samples/bpf/trace_output_user.c
+++ b/samples/bpf/trace_output_user.c
@@ -18,9 +18,6 @@
 #include <libbpf.h>
 #include "bpf_load.h"
 #include "perf-sys.h"
-#include "trace_helpers.h"
-
-static int pmu_fd;
 
 static __u64 time_get_ns(void)
 {
@@ -31,12 +28,12 @@ static __u64 time_get_ns(void)
 }
 
 static __u64 start_time;
+static __u64 cnt;
 
 #define MAX_CNT 100000ll
 
-static int print_bpf_output(void *data, int size)
+static void print_bpf_output(void *ctx, int cpu, void *data, __u32 size)
 {
-	static __u64 cnt;
 	struct {
 		__u64 pid;
 		__u64 cookie;
@@ -45,7 +42,7 @@ static int print_bpf_output(void *data, int size)
 	if (e->cookie != 0x12345678) {
 		printf("BUG pid %llx cookie %llx sized %d\n",
 		       e->pid, e->cookie, size);
-		return LIBBPF_PERF_EVENT_ERROR;
+		return;
 	}
 
 	cnt++;
@@ -53,30 +50,14 @@ static int print_bpf_output(void *data, int size)
 	if (cnt == MAX_CNT) {
 		printf("recv %lld events per sec\n",
 		       MAX_CNT * 1000000000ll / (time_get_ns() - start_time));
-		return LIBBPF_PERF_EVENT_DONE;
+		return;
 	}
-
-	return LIBBPF_PERF_EVENT_CONT;
-}
-
-static void test_bpf_perf_event(void)
-{
-	struct perf_event_attr attr = {
-		.sample_type = PERF_SAMPLE_RAW,
-		.type = PERF_TYPE_SOFTWARE,
-		.config = PERF_COUNT_SW_BPF_OUTPUT,
-	};
-	int key = 0;
-
-	pmu_fd = sys_perf_event_open(&attr, -1/*pid*/, 0/*cpu*/, -1/*group_fd*/, 0);
-
-	assert(pmu_fd >= 0);
-	assert(bpf_map_update_elem(map_fd[0], &key, &pmu_fd, BPF_ANY) == 0);
-	ioctl(pmu_fd, PERF_EVENT_IOC_ENABLE, 0);
 }
 
 int main(int argc, char **argv)
 {
+	struct perf_buffer_opts pb_opts = {};
+	struct perf_buffer *pb;
 	char filename[256];
 	FILE *f;
 	int ret;
@@ -88,16 +69,20 @@ int main(int argc, char **argv)
 		return 1;
 	}
 
-	test_bpf_perf_event();
-
-	if (perf_event_mmap(pmu_fd) < 0)
+	pb_opts.sample_cb = print_bpf_output;
+	pb = perf_buffer__new(map_fd[0], 8, &pb_opts);
+	ret = libbpf_get_error(pb);
+	if (ret) {
+		printf("failed to setup perf_buffer: %d\n", ret);
 		return 1;
+	}
 
 	f = popen("taskset 1 dd if=/dev/zero of=/dev/null", "r");
 	(void) f;
 
 	start_time = time_get_ns();
-	ret = perf_event_poller(pmu_fd, print_bpf_output);
+	while ((ret = perf_buffer__poll(pb, 1000)) >= 0 && cnt < MAX_CNT) {
+	}
 	kill(0, SIGINT);
 	return ret;
 }
-- 
2.17.1


^ permalink raw reply related	[flat|nested] 8+ messages in thread

* [PATCH v2 bpf-next 5/5] selftests/bpf: remove perf buffer helpers
  2019-07-23 21:34 [PATCH v2 bpf-next 0/5] switch samples and tests to libbpf perf buffer API Andrii Nakryiko
                   ` (3 preceding siblings ...)
  2019-07-23 21:34 ` [PATCH v2 bpf-next 4/5] samples/bpf: switch trace_output sample " Andrii Nakryiko
@ 2019-07-23 21:34 ` Andrii Nakryiko
  2019-07-23 23:09 ` [PATCH v2 bpf-next 0/5] switch samples and tests to libbpf perf buffer API Alexei Starovoitov
  5 siblings, 0 replies; 8+ messages in thread
From: Andrii Nakryiko @ 2019-07-23 21:34 UTC (permalink / raw)
  To: bpf, netdev, ast, daniel, songliubraving
  Cc: andrii.nakryiko, kernel-team, Andrii Nakryiko

libbpf's perf_buffer API supersedes trace_helper.h's helpers.
Remove those helpers after all existing users were already moved to
perf_buffer API.

Signed-off-by: Andrii Nakryiko <andriin@fb.com>
Acked-by: Song Liu <songliubraving@fb.com>
---
 tools/testing/selftests/bpf/trace_helpers.c | 125 --------------------
 tools/testing/selftests/bpf/trace_helpers.h |   9 --
 2 files changed, 134 deletions(-)

diff --git a/tools/testing/selftests/bpf/trace_helpers.c b/tools/testing/selftests/bpf/trace_helpers.c
index b47f205f0310..7f989b3e4e22 100644
--- a/tools/testing/selftests/bpf/trace_helpers.c
+++ b/tools/testing/selftests/bpf/trace_helpers.c
@@ -86,128 +86,3 @@ long ksym_get_addr(const char *name)
 
 	return 0;
 }
-
-static int page_size;
-static int page_cnt = 8;
-static struct perf_event_mmap_page *header;
-
-int perf_event_mmap_header(int fd, struct perf_event_mmap_page **header)
-{
-	void *base;
-	int mmap_size;
-
-	page_size = getpagesize();
-	mmap_size = page_size * (page_cnt + 1);
-
-	base = mmap(NULL, mmap_size, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0);
-	if (base == MAP_FAILED) {
-		printf("mmap err\n");
-		return -1;
-	}
-
-	*header = base;
-	return 0;
-}
-
-int perf_event_mmap(int fd)
-{
-	return perf_event_mmap_header(fd, &header);
-}
-
-static int perf_event_poll(int fd)
-{
-	struct pollfd pfd = { .fd = fd, .events = POLLIN };
-
-	return poll(&pfd, 1, 1000);
-}
-
-struct perf_event_sample {
-	struct perf_event_header header;
-	__u32 size;
-	char data[];
-};
-
-static enum bpf_perf_event_ret
-bpf_perf_event_print(struct perf_event_header *hdr, void *private_data)
-{
-	struct perf_event_sample *e = (struct perf_event_sample *)hdr;
-	perf_event_print_fn fn = private_data;
-	int ret;
-
-	if (e->header.type == PERF_RECORD_SAMPLE) {
-		ret = fn(e->data, e->size);
-		if (ret != LIBBPF_PERF_EVENT_CONT)
-			return ret;
-	} else if (e->header.type == PERF_RECORD_LOST) {
-		struct {
-			struct perf_event_header header;
-			__u64 id;
-			__u64 lost;
-		} *lost = (void *) e;
-		printf("lost %lld events\n", lost->lost);
-	} else {
-		printf("unknown event type=%d size=%d\n",
-		       e->header.type, e->header.size);
-	}
-
-	return LIBBPF_PERF_EVENT_CONT;
-}
-
-int perf_event_poller(int fd, perf_event_print_fn output_fn)
-{
-	enum bpf_perf_event_ret ret;
-	void *buf = NULL;
-	size_t len = 0;
-
-	for (;;) {
-		perf_event_poll(fd);
-		ret = bpf_perf_event_read_simple(header, page_cnt * page_size,
-						 page_size, &buf, &len,
-						 bpf_perf_event_print,
-						 output_fn);
-		if (ret != LIBBPF_PERF_EVENT_CONT)
-			break;
-	}
-	free(buf);
-
-	return ret;
-}
-
-int perf_event_poller_multi(int *fds, struct perf_event_mmap_page **headers,
-			    int num_fds, perf_event_print_fn output_fn)
-{
-	enum bpf_perf_event_ret ret;
-	struct pollfd *pfds;
-	void *buf = NULL;
-	size_t len = 0;
-	int i;
-
-	pfds = calloc(num_fds, sizeof(*pfds));
-	if (!pfds)
-		return LIBBPF_PERF_EVENT_ERROR;
-
-	for (i = 0; i < num_fds; i++) {
-		pfds[i].fd = fds[i];
-		pfds[i].events = POLLIN;
-	}
-
-	for (;;) {
-		poll(pfds, num_fds, 1000);
-		for (i = 0; i < num_fds; i++) {
-			if (!pfds[i].revents)
-				continue;
-
-			ret = bpf_perf_event_read_simple(headers[i],
-							 page_cnt * page_size,
-							 page_size, &buf, &len,
-							 bpf_perf_event_print,
-							 output_fn);
-			if (ret != LIBBPF_PERF_EVENT_CONT)
-				break;
-		}
-	}
-	free(buf);
-	free(pfds);
-
-	return ret;
-}
diff --git a/tools/testing/selftests/bpf/trace_helpers.h b/tools/testing/selftests/bpf/trace_helpers.h
index 18924f23db1b..aa4dcfe18050 100644
--- a/tools/testing/selftests/bpf/trace_helpers.h
+++ b/tools/testing/selftests/bpf/trace_helpers.h
@@ -3,7 +3,6 @@
 #define __TRACE_HELPER_H
 
 #include <libbpf.h>
-#include <linux/perf_event.h>
 
 struct ksym {
 	long addr;
@@ -14,12 +13,4 @@ int load_kallsyms(void);
 struct ksym *ksym_search(long key);
 long ksym_get_addr(const char *name);
 
-typedef enum bpf_perf_event_ret (*perf_event_print_fn)(void *data, int size);
-
-int perf_event_mmap(int fd);
-int perf_event_mmap_header(int fd, struct perf_event_mmap_page **header);
-/* return LIBBPF_PERF_EVENT_DONE or LIBBPF_PERF_EVENT_ERROR */
-int perf_event_poller(int fd, perf_event_print_fn output_fn);
-int perf_event_poller_multi(int *fds, struct perf_event_mmap_page **headers,
-			    int num_fds, perf_event_print_fn output_fn);
 #endif
-- 
2.17.1


^ permalink raw reply related	[flat|nested] 8+ messages in thread

* Re: [PATCH v2 bpf-next 1/5] selftests/bpf: convert test_get_stack_raw_tp to perf_buffer API
  2019-07-23 21:34 ` [PATCH v2 bpf-next 1/5] selftests/bpf: convert test_get_stack_raw_tp to perf_buffer API Andrii Nakryiko
@ 2019-07-23 22:02   ` Song Liu
  0 siblings, 0 replies; 8+ messages in thread
From: Song Liu @ 2019-07-23 22:02 UTC (permalink / raw)
  To: Andrii Nakryiko
  Cc: bpf, Networking, Alexei Starovoitov, daniel, andrii.nakryiko,
	Kernel Team



> On Jul 23, 2019, at 2:34 PM, Andrii Nakryiko <andriin@fb.com> wrote:
> 
> Convert test_get_stack_raw_tp test to new perf_buffer API.
> 
> Signed-off-by: Andrii Nakryiko <andriin@fb.com>

Acked-by: Song Liu <songliubraving@fb.com>

^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: [PATCH v2 bpf-next 0/5] switch samples and tests to libbpf perf buffer API
  2019-07-23 21:34 [PATCH v2 bpf-next 0/5] switch samples and tests to libbpf perf buffer API Andrii Nakryiko
                   ` (4 preceding siblings ...)
  2019-07-23 21:34 ` [PATCH v2 bpf-next 5/5] selftests/bpf: remove perf buffer helpers Andrii Nakryiko
@ 2019-07-23 23:09 ` Alexei Starovoitov
  5 siblings, 0 replies; 8+ messages in thread
From: Alexei Starovoitov @ 2019-07-23 23:09 UTC (permalink / raw)
  To: Andrii Nakryiko, bpf, netdev, daniel, Song Liu
  Cc: andrii.nakryiko, Kernel Team

On 7/23/19 2:34 PM, Andrii Nakryiko wrote:
> There were few more tests and samples that were using custom perf buffer setup
> code from trace_helpers.h. This patch set gets rid of all the usages of those
> and removes helpers themselves. Libbpf provides nicer, but equally powerful
> set of APIs to work with perf ring buffers, so let's have all the samples use
> 
> v1->v2:
> - make logging message one long line instead of two (Song).

Applied. Thanks

^ permalink raw reply	[flat|nested] 8+ messages in thread

end of thread, other threads:[~2019-07-23 23:09 UTC | newest]

Thread overview: 8+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2019-07-23 21:34 [PATCH v2 bpf-next 0/5] switch samples and tests to libbpf perf buffer API Andrii Nakryiko
2019-07-23 21:34 ` [PATCH v2 bpf-next 1/5] selftests/bpf: convert test_get_stack_raw_tp to perf_buffer API Andrii Nakryiko
2019-07-23 22:02   ` Song Liu
2019-07-23 21:34 ` [PATCH v2 bpf-next 2/5] selftests/bpf: switch test_tcpnotify " Andrii Nakryiko
2019-07-23 21:34 ` [PATCH v2 bpf-next 3/5] samples/bpf: convert xdp_sample_pkts_user " Andrii Nakryiko
2019-07-23 21:34 ` [PATCH v2 bpf-next 4/5] samples/bpf: switch trace_output sample " Andrii Nakryiko
2019-07-23 21:34 ` [PATCH v2 bpf-next 5/5] selftests/bpf: remove perf buffer helpers Andrii Nakryiko
2019-07-23 23:09 ` [PATCH v2 bpf-next 0/5] switch samples and tests to libbpf perf buffer API Alexei Starovoitov

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.