1// SPDX-License-Identifier: GPL-2.0 2/* Copyright (c) 2021 Facebook */ 3 4#include <argp.h> 5#include "bench.h" 6#include "bpf_loop_bench.skel.h" 7 8/* BPF triggering benchmarks */ 9static struct ctx { 10 struct bpf_loop_bench *skel; 11} ctx; 12 13static struct { 14 __u32 nr_loops; 15} args = { 16 .nr_loops = 10, 17}; 18 19enum { 20 ARG_NR_LOOPS = 4000, 21}; 22 23static const struct argp_option opts[] = { 24 { "nr_loops", ARG_NR_LOOPS, "nr_loops", 0, 25 "Set number of loops for the bpf_loop helper"}, 26 {}, 27}; 28 29static error_t parse_arg(int key, char *arg, struct argp_state *state) 30{ 31 switch (key) { 32 case ARG_NR_LOOPS: 33 args.nr_loops = strtol(arg, NULL, 10); 34 break; 35 default: 36 return ARGP_ERR_UNKNOWN; 37 } 38 39 return 0; 40} 41 42/* exported into benchmark runner */ 43const struct argp bench_bpf_loop_argp = { 44 .options = opts, 45 .parser = parse_arg, 46}; 47 48static void validate(void) 49{ 50 if (env.consumer_cnt != 0) { 51 fprintf(stderr, "benchmark doesn't support consumer!\n"); 52 exit(1); 53 } 54} 55 56static void *producer(void *input) 57{ 58 while (true) 59 /* trigger the bpf program */ 60 syscall(__NR_getpgid); 61 62 return NULL; 63} 64 65static void measure(struct bench_res *res) 66{ 67 res->hits = atomic_swap(&ctx.skel->bss->hits, 0); 68} 69 70static void setup(void) 71{ 72 struct bpf_link *link; 73 74 setup_libbpf(); 75 76 ctx.skel = bpf_loop_bench__open_and_load(); 77 if (!ctx.skel) { 78 fprintf(stderr, "failed to open skeleton\n"); 79 exit(1); 80 } 81 82 link = bpf_program__attach(ctx.skel->progs.benchmark); 83 if (!link) { 84 fprintf(stderr, "failed to attach program!\n"); 85 exit(1); 86 } 87 88 ctx.skel->bss->nr_loops = args.nr_loops; 89} 90 91const struct bench bench_bpf_loop = { 92 .name = "bpf-loop", 93 .argp = &bench_bpf_loop_argp, 94 .validate = validate, 95 .setup = setup, 96 .producer_thread = producer, 97 .measure = measure, 98 .report_progress = ops_report_progress, 99 .report_final = ops_report_final, 100}; 101