From: Luca Boccassi Date: Fri, 8 Jan 2021 23:47:03 +0000 (+0000) Subject: bpf: zero bpf_attr before initialization X-Git-Tag: v248-rc1~389 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=28abf5ad3483a417d3d4de561533d282493a7f2a;p=thirdparty%2Fsystemd.git bpf: zero bpf_attr before initialization When building with Clang and using structured initialization, the bpf_attr union is not zero-padded, so the kernel misdetects it as an unsupported extension. zero it until Clang's behaviour matches GCC. Do not skip the test on Github Actions anymore. --- diff --git a/src/shared/bpf-program.c b/src/shared/bpf-program.c index 067f26d2f0b..9da8c109b84 100644 --- a/src/shared/bpf-program.c +++ b/src/shared/bpf-program.c @@ -76,6 +76,11 @@ int bpf_program_load_kernel(BPFProgram *p, char *log_buf, size_t log_size) { return 0; } + // FIXME: Clang doesn't 0-pad with structured initialization, causing + // the kernel to reject the bpf_attr as invalid. See: + // https://github.com/torvalds/linux/blob/v5.9/kernel/bpf/syscall.c#L65 + // Ideally it should behave like GCC, so that we can remove these workarounds. + zero(attr); attr = (union bpf_attr) { .prog_type = p->prog_type, .insns = PTR_TO_UINT64(p->instructions), @@ -101,6 +106,7 @@ int bpf_program_load_from_bpf_fs(BPFProgram *p, const char *path) { if (p->kernel_fd >= 0) /* don't overwrite an assembled or loaded program */ return -EBUSY; + zero(attr); attr = (union bpf_attr) { .pathname = PTR_TO_UINT64(path), }; @@ -158,6 +164,7 @@ int bpf_program_cgroup_attach(BPFProgram *p, int type, const char *path, uint32_ if (fd < 0) return -errno; + zero(attr); attr = (union bpf_attr) { .attach_type = type, .target_fd = fd, @@ -194,6 +201,7 @@ int bpf_program_cgroup_detach(BPFProgram *p) { } else { union bpf_attr attr; + zero(attr); attr = (union bpf_attr) { .attach_type = p->attached_type, .target_fd = fd, diff --git a/src/test/test-bpf-firewall.c b/src/test/test-bpf-firewall.c index d129bb36295..cb7d8398a81 100644 --- a/src/test/test-bpf-firewall.c +++ b/src/test/test-bpf-firewall.c @@ -37,16 +37,6 @@ int main(int argc, char *argv[]) { if (detect_container() > 0) return log_tests_skipped("test-bpf-firewall fails inside LXC and Docker containers: https://github.com/systemd/systemd/issues/9666"); -#ifdef __clang__ - /* FIXME: This test is for (currently unknown) reasons failing in both - * sanitized and unsanitized clang runs. Until the issue is resolved, - * let's skip the test when running on GH Actions and compiled with - * clang. - */ - if (strstr_ptr(ci_environment(), "github-actions")) - return log_tests_skipped("Skipping test on GH Actions"); -#endif - assert_se(getrlimit(RLIMIT_MEMLOCK, &rl) >= 0); rl.rlim_cur = rl.rlim_max = MAX(rl.rlim_max, CAN_MEMLOCK_SIZE); (void) setrlimit(RLIMIT_MEMLOCK, &rl);