From: Lennart Poettering Date: Tue, 20 Feb 2018 18:19:57 +0000 (+0100) Subject: bpf-program: make bpf_program_load_kernel() idempotent X-Git-Tag: v238~68^2~2 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=e0ad39fc52ed851974dd8f522a45a2539b524bed;p=thirdparty%2Fsystemd.git bpf-program: make bpf_program_load_kernel() idempotent Let's "seal" off the BPF program as soo as bpf_program_load_kernel() is called, which allows us to make it idempotent: since the program can't be modified anymore after being turned into a kernel object it's safe to shortcut behaviour if called multiple times. --- diff --git a/src/basic/bpf-program.c b/src/basic/bpf-program.c index 4745950e644..4c128c6d6b9 100644 --- a/src/basic/bpf-program.c +++ b/src/basic/bpf-program.c @@ -28,6 +28,7 @@ #include "fd-util.h" #include "log.h" #include "missing.h" +#include "util.h" int bpf_program_new(uint32_t prog_type, BPFProgram **ret) { _cleanup_(bpf_program_unrefp) BPFProgram *p = NULL; @@ -58,6 +59,9 @@ int bpf_program_add_instructions(BPFProgram *p, const struct bpf_insn *instructi assert(p); + if (p->kernel_fd >= 0) /* don't allow modification after we uploaded things to the kernel */ + return -EBUSY; + if (!GREEDY_REALLOC(p->instructions, p->allocated, p->n_instructions + count)) return -ENOMEM; @@ -72,8 +76,10 @@ int bpf_program_load_kernel(BPFProgram *p, char *log_buf, size_t log_size) { assert(p); - if (p->kernel_fd >= 0) - return -EBUSY; + if (p->kernel_fd >= 0) { /* make this idempotent */ + memzero(log_buf, log_size); + return 0; + } attr = (union bpf_attr) { .prog_type = p->prog_type,