From 73964e9085bbea517a675d5d8ceeb1e609a34748 Mon Sep 17 00:00:00 2001 From: Jordan Rife Date: Fri, 10 May 2024 14:02:18 -0500 Subject: [PATCH 01/17] selftests/bpf: Migrate recvmsg* return code tests to verifier_sock_addr.c This set of tests check that the BPF verifier rejects programs with invalid return codes (recvmsg4 and recvmsg6 hooks can only return 1). This patch replaces the tests in test_sock_addr.c with verifier_sock_addr.c, a new verifier prog_tests for sockaddr hooks, in a step towards fully retiring test_sock_addr.c. Signed-off-by: Jordan Rife Link: https://lore.kernel.org/r/20240510190246.3247730-2-jrife@google.com Signed-off-by: Alexei Starovoitov --- .../selftests/bpf/prog_tests/verifier.c | 2 + .../selftests/bpf/progs/verifier_sock_addr.c | 37 ++++++++++ tools/testing/selftests/bpf/test_sock_addr.c | 70 ------------------- 3 files changed, 39 insertions(+), 70 deletions(-) create mode 100644 tools/testing/selftests/bpf/progs/verifier_sock_addr.c diff --git a/tools/testing/selftests/bpf/prog_tests/verifier.c b/tools/testing/selftests/bpf/prog_tests/verifier.c index c4f9f306646e..c60db8beeb73 100644 --- a/tools/testing/selftests/bpf/prog_tests/verifier.c +++ b/tools/testing/selftests/bpf/prog_tests/verifier.c @@ -66,6 +66,7 @@ #include "verifier_sdiv.skel.h" #include "verifier_search_pruning.skel.h" #include "verifier_sock.skel.h" +#include "verifier_sock_addr.skel.h" #include "verifier_spill_fill.skel.h" #include "verifier_spin_lock.skel.h" #include "verifier_stack_ptr.skel.h" @@ -181,6 +182,7 @@ void test_verifier_scalar_ids(void) { RUN(verifier_scalar_ids); } void test_verifier_sdiv(void) { RUN(verifier_sdiv); } void test_verifier_search_pruning(void) { RUN(verifier_search_pruning); } void test_verifier_sock(void) { RUN(verifier_sock); } +void test_verifier_sock_addr(void) { RUN(verifier_sock_addr); } void test_verifier_spill_fill(void) { RUN(verifier_spill_fill); } void test_verifier_spin_lock(void) { RUN(verifier_spin_lock); } void test_verifier_stack_ptr(void) { RUN(verifier_stack_ptr); } diff --git a/tools/testing/selftests/bpf/progs/verifier_sock_addr.c b/tools/testing/selftests/bpf/progs/verifier_sock_addr.c new file mode 100644 index 000000000000..5081fa723d3a --- /dev/null +++ b/tools/testing/selftests/bpf/progs/verifier_sock_addr.c @@ -0,0 +1,37 @@ +// SPDX-License-Identifier: GPL-2.0 +/* Copyright (c) 2024 Google LLC */ + +#include +#include +#include +#include "bpf_misc.h" + +SEC("cgroup/recvmsg4") +__success +int recvmsg4_good_return_code(struct bpf_sock_addr *ctx) +{ + return 1; +} + +SEC("cgroup/recvmsg4") +__failure __msg("At program exit the register R0 has smin=0 smax=0 should have been in [1, 1]") +int recvmsg4_bad_return_code(struct bpf_sock_addr *ctx) +{ + return 0; +} + +SEC("cgroup/recvmsg6") +__success +int recvmsg6_good_return_code(struct bpf_sock_addr *ctx) +{ + return 1; +} + +SEC("cgroup/recvmsg6") +__failure __msg("At program exit the register R0 has smin=0 smax=0 should have been in [1, 1]") +int recvmsg6_bad_return_code(struct bpf_sock_addr *ctx) +{ + return 0; +} + +char _license[] SEC("license") = "GPL"; diff --git a/tools/testing/selftests/bpf/test_sock_addr.c b/tools/testing/selftests/bpf/test_sock_addr.c index aa2198a0f24d..40e33167bec2 100644 --- a/tools/testing/selftests/bpf/test_sock_addr.c +++ b/tools/testing/selftests/bpf/test_sock_addr.c @@ -94,8 +94,6 @@ static int connect4_prog_load(const struct sock_addr_test *test); static int connect6_prog_load(const struct sock_addr_test *test); static int sendmsg_allow_prog_load(const struct sock_addr_test *test); static int sendmsg_deny_prog_load(const struct sock_addr_test *test); -static int recvmsg_allow_prog_load(const struct sock_addr_test *test); -static int recvmsg_deny_prog_load(const struct sock_addr_test *test); static int sendmsg4_rw_asm_prog_load(const struct sock_addr_test *test); static int sendmsg6_rw_asm_prog_load(const struct sock_addr_test *test); static int sendmsg6_rw_v4mapped_prog_load(const struct sock_addr_test *test); @@ -373,64 +371,6 @@ static struct sock_addr_test tests[] = { SRC6_REWRITE_IP, SYSCALL_EPERM, }, - - /* recvmsg */ - { - "recvmsg4: return code ok", - recvmsg_allow_prog_load, - BPF_CGROUP_UDP4_RECVMSG, - BPF_CGROUP_UDP4_RECVMSG, - AF_INET, - SOCK_DGRAM, - NULL, - 0, - NULL, - 0, - NULL, - ATTACH_OKAY, - }, - { - "recvmsg4: return code !ok", - recvmsg_deny_prog_load, - BPF_CGROUP_UDP4_RECVMSG, - BPF_CGROUP_UDP4_RECVMSG, - AF_INET, - SOCK_DGRAM, - NULL, - 0, - NULL, - 0, - NULL, - LOAD_REJECT, - }, - { - "recvmsg6: return code ok", - recvmsg_allow_prog_load, - BPF_CGROUP_UDP6_RECVMSG, - BPF_CGROUP_UDP6_RECVMSG, - AF_INET6, - SOCK_DGRAM, - NULL, - 0, - NULL, - 0, - NULL, - ATTACH_OKAY, - }, - { - "recvmsg6: return code !ok", - recvmsg_deny_prog_load, - BPF_CGROUP_UDP6_RECVMSG, - BPF_CGROUP_UDP6_RECVMSG, - AF_INET6, - SOCK_DGRAM, - NULL, - 0, - NULL, - 0, - NULL, - LOAD_REJECT, - }, }; static int load_insns(const struct sock_addr_test *test, @@ -527,16 +467,6 @@ static int sendmsg_deny_prog_load(const struct sock_addr_test *test) return xmsg_ret_only_prog_load(test, /*rc*/ 0); } -static int recvmsg_allow_prog_load(const struct sock_addr_test *test) -{ - return xmsg_ret_only_prog_load(test, /*rc*/ 1); -} - -static int recvmsg_deny_prog_load(const struct sock_addr_test *test) -{ - return xmsg_ret_only_prog_load(test, /*rc*/ 0); -} - static int sendmsg4_rw_asm_prog_load(const struct sock_addr_test *test) { struct sockaddr_in dst4_rw_addr; From 86b65c6db0190fb6c119e83da4de0eccf74fb1ff Mon Sep 17 00:00:00 2001 From: Jordan Rife Date: Fri, 10 May 2024 14:02:19 -0500 Subject: [PATCH 02/17] selftests/bpf: Use program name for skel load/destroy functions In preparation to migrate tests from bpf/test_sock_addr.c to sock_addr.c, update BPF_SKEL_FUNCS so that it generates functions based on prog_name instead of skel_name. This allows us to differentiate between programs in the same skeleton. Signed-off-by: Jordan Rife Link: https://lore.kernel.org/r/20240510190246.3247730-3-jrife@google.com Signed-off-by: Alexei Starovoitov --- .../selftests/bpf/prog_tests/sock_addr.c | 96 ++++++++++--------- 1 file changed, 50 insertions(+), 46 deletions(-) diff --git a/tools/testing/selftests/bpf/prog_tests/sock_addr.c b/tools/testing/selftests/bpf/prog_tests/sock_addr.c index 9c709c33f889..039c3e38e1bc 100644 --- a/tools/testing/selftests/bpf/prog_tests/sock_addr.c +++ b/tools/testing/selftests/bpf/prog_tests/sock_addr.c @@ -357,7 +357,7 @@ struct sock_addr_test { }; #define BPF_SKEL_FUNCS(skel_name, prog_name) \ -static void *skel_name##_load(int cgroup_fd) \ +static void *prog_name##_load(int cgroup_fd) \ { \ struct skel_name *skel; \ skel = skel_name##__open_and_load(); \ @@ -372,7 +372,7 @@ cleanup: \ skel_name##__destroy(skel); \ return NULL; \ } \ -static void skel_name##_destroy(void *skel) \ +static void prog_name##_destroy(void *skel) \ { \ skel_name##__destroy(skel); \ } @@ -396,8 +396,8 @@ static struct sock_addr_test tests[] = { { SOCK_ADDR_TEST_BIND, "bind4: bind (stream)", - bind4_prog_load, - bind4_prog_destroy, + bind_v4_prog_load, + bind_v4_prog_destroy, &user_ops, AF_INET, SOCK_STREAM, @@ -405,12 +405,13 @@ static struct sock_addr_test tests[] = { SERV4_PORT, SERV4_REWRITE_IP, SERV4_REWRITE_PORT, + NULL, }, { SOCK_ADDR_TEST_BIND, "bind4: bind (dgram)", - bind4_prog_load, - bind4_prog_destroy, + bind_v4_prog_load, + bind_v4_prog_destroy, &user_ops, AF_INET, SOCK_DGRAM, @@ -418,12 +419,13 @@ static struct sock_addr_test tests[] = { SERV4_PORT, SERV4_REWRITE_IP, SERV4_REWRITE_PORT, + NULL, }, { SOCK_ADDR_TEST_BIND, "bind6: bind (stream)", - bind6_prog_load, - bind6_prog_destroy, + bind_v6_prog_load, + bind_v6_prog_destroy, &user_ops, AF_INET6, SOCK_STREAM, @@ -431,12 +433,13 @@ static struct sock_addr_test tests[] = { SERV6_PORT, SERV6_REWRITE_IP, SERV6_REWRITE_PORT, + NULL, }, { SOCK_ADDR_TEST_BIND, "bind6: bind (dgram)", - bind6_prog_load, - bind6_prog_destroy, + bind_v6_prog_load, + bind_v6_prog_destroy, &user_ops, AF_INET6, SOCK_DGRAM, @@ -444,14 +447,15 @@ static struct sock_addr_test tests[] = { SERV6_PORT, SERV6_REWRITE_IP, SERV6_REWRITE_PORT, + NULL, }, /* bind - kernel calls */ { SOCK_ADDR_TEST_BIND, "bind4: kernel_bind (stream)", - bind4_prog_load, - bind4_prog_destroy, + bind_v4_prog_load, + bind_v4_prog_destroy, &kern_ops_sock_sendmsg, AF_INET, SOCK_STREAM, @@ -463,8 +467,8 @@ static struct sock_addr_test tests[] = { { SOCK_ADDR_TEST_BIND, "bind4: kernel_bind (dgram)", - bind4_prog_load, - bind4_prog_destroy, + bind_v4_prog_load, + bind_v4_prog_destroy, &kern_ops_sock_sendmsg, AF_INET, SOCK_DGRAM, @@ -476,8 +480,8 @@ static struct sock_addr_test tests[] = { { SOCK_ADDR_TEST_BIND, "bind6: kernel_bind (stream)", - bind6_prog_load, - bind6_prog_destroy, + bind_v6_prog_load, + bind_v6_prog_destroy, &kern_ops_sock_sendmsg, AF_INET6, SOCK_STREAM, @@ -489,8 +493,8 @@ static struct sock_addr_test tests[] = { { SOCK_ADDR_TEST_BIND, "bind6: kernel_bind (dgram)", - bind6_prog_load, - bind6_prog_destroy, + bind_v6_prog_load, + bind_v6_prog_destroy, &kern_ops_sock_sendmsg, AF_INET6, SOCK_DGRAM, @@ -504,8 +508,8 @@ static struct sock_addr_test tests[] = { { SOCK_ADDR_TEST_CONNECT, "connect4: connect (stream)", - connect4_prog_load, - connect4_prog_destroy, + connect_v4_prog_load, + connect_v4_prog_destroy, &user_ops, AF_INET, SOCK_STREAM, @@ -518,8 +522,8 @@ static struct sock_addr_test tests[] = { { SOCK_ADDR_TEST_CONNECT, "connect4: connect (dgram)", - connect4_prog_load, - connect4_prog_destroy, + connect_v4_prog_load, + connect_v4_prog_destroy, &user_ops, AF_INET, SOCK_DGRAM, @@ -532,8 +536,8 @@ static struct sock_addr_test tests[] = { { SOCK_ADDR_TEST_CONNECT, "connect6: connect (stream)", - connect6_prog_load, - connect6_prog_destroy, + connect_v6_prog_load, + connect_v6_prog_destroy, &user_ops, AF_INET6, SOCK_STREAM, @@ -546,8 +550,8 @@ static struct sock_addr_test tests[] = { { SOCK_ADDR_TEST_CONNECT, "connect6: connect (dgram)", - connect6_prog_load, - connect6_prog_destroy, + connect_v6_prog_load, + connect_v6_prog_destroy, &user_ops, AF_INET6, SOCK_DGRAM, @@ -576,8 +580,8 @@ static struct sock_addr_test tests[] = { { SOCK_ADDR_TEST_CONNECT, "connect4: kernel_connect (stream)", - connect4_prog_load, - connect4_prog_destroy, + connect_v4_prog_load, + connect_v4_prog_destroy, &kern_ops_sock_sendmsg, AF_INET, SOCK_STREAM, @@ -590,8 +594,8 @@ static struct sock_addr_test tests[] = { { SOCK_ADDR_TEST_CONNECT, "connect4: kernel_connect (dgram)", - connect4_prog_load, - connect4_prog_destroy, + connect_v4_prog_load, + connect_v4_prog_destroy, &kern_ops_sock_sendmsg, AF_INET, SOCK_DGRAM, @@ -604,8 +608,8 @@ static struct sock_addr_test tests[] = { { SOCK_ADDR_TEST_CONNECT, "connect6: kernel_connect (stream)", - connect6_prog_load, - connect6_prog_destroy, + connect_v6_prog_load, + connect_v6_prog_destroy, &kern_ops_sock_sendmsg, AF_INET6, SOCK_STREAM, @@ -618,8 +622,8 @@ static struct sock_addr_test tests[] = { { SOCK_ADDR_TEST_CONNECT, "connect6: kernel_connect (dgram)", - connect6_prog_load, - connect6_prog_destroy, + connect_v6_prog_load, + connect_v6_prog_destroy, &kern_ops_sock_sendmsg, AF_INET6, SOCK_DGRAM, @@ -648,8 +652,8 @@ static struct sock_addr_test tests[] = { { SOCK_ADDR_TEST_SENDMSG, "sendmsg4: sendmsg (dgram)", - sendmsg4_prog_load, - sendmsg4_prog_destroy, + sendmsg_v4_prog_load, + sendmsg_v4_prog_destroy, &user_ops, AF_INET, SOCK_DGRAM, @@ -662,8 +666,8 @@ static struct sock_addr_test tests[] = { { SOCK_ADDR_TEST_SENDMSG, "sendmsg6: sendmsg (dgram)", - sendmsg6_prog_load, - sendmsg6_prog_destroy, + sendmsg_v6_prog_load, + sendmsg_v6_prog_destroy, &user_ops, AF_INET6, SOCK_DGRAM, @@ -692,8 +696,8 @@ static struct sock_addr_test tests[] = { { SOCK_ADDR_TEST_SENDMSG, "sendmsg4: sock_sendmsg (dgram)", - sendmsg4_prog_load, - sendmsg4_prog_destroy, + sendmsg_v4_prog_load, + sendmsg_v4_prog_destroy, &kern_ops_sock_sendmsg, AF_INET, SOCK_DGRAM, @@ -706,8 +710,8 @@ static struct sock_addr_test tests[] = { { SOCK_ADDR_TEST_SENDMSG, "sendmsg6: sock_sendmsg (dgram)", - sendmsg6_prog_load, - sendmsg6_prog_destroy, + sendmsg_v6_prog_load, + sendmsg_v6_prog_destroy, &kern_ops_sock_sendmsg, AF_INET6, SOCK_DGRAM, @@ -736,8 +740,8 @@ static struct sock_addr_test tests[] = { { SOCK_ADDR_TEST_SENDMSG, "sendmsg4: kernel_sendmsg (dgram)", - sendmsg4_prog_load, - sendmsg4_prog_destroy, + sendmsg_v4_prog_load, + sendmsg_v4_prog_destroy, &kern_ops_kernel_sendmsg, AF_INET, SOCK_DGRAM, @@ -750,8 +754,8 @@ static struct sock_addr_test tests[] = { { SOCK_ADDR_TEST_SENDMSG, "sendmsg6: kernel_sendmsg (dgram)", - sendmsg6_prog_load, - sendmsg6_prog_destroy, + sendmsg_v6_prog_load, + sendmsg_v6_prog_destroy, &kern_ops_kernel_sendmsg, AF_INET6, SOCK_DGRAM, From 5eff48f33fb733de9b88a5381e0428f3e873c670 Mon Sep 17 00:00:00 2001 From: Jordan Rife Date: Fri, 10 May 2024 14:02:20 -0500 Subject: [PATCH 03/17] selftests/bpf: Handle LOAD_REJECT test cases In preparation to move test cases from bpf/test_sock_addr.c that expect LOAD_REJECT, this patch adds expected_attach_type and extends load_fn to accept an expected attach type and a flag indicating whether or not rejection is expected. Signed-off-by: Jordan Rife Link: https://lore.kernel.org/r/20240510190246.3247730-4-jrife@google.com Signed-off-by: Alexei Starovoitov --- .../selftests/bpf/prog_tests/sock_addr.c | 103 +++++++++++++++++- 1 file changed, 98 insertions(+), 5 deletions(-) diff --git a/tools/testing/selftests/bpf/prog_tests/sock_addr.c b/tools/testing/selftests/bpf/prog_tests/sock_addr.c index 039c3e38e1bc..3033641fd756 100644 --- a/tools/testing/selftests/bpf/prog_tests/sock_addr.c +++ b/tools/testing/selftests/bpf/prog_tests/sock_addr.c @@ -52,7 +52,9 @@ enum sock_addr_test_type { SOCK_ADDR_TEST_GETPEERNAME, }; -typedef void *(*load_fn)(int cgroup_fd); +typedef void *(*load_fn)(int cgroup_fd, + enum bpf_attach_type attach_type, + bool expect_reject); typedef void (*destroy_fn)(void *skel); static int cmp_addr(const struct sockaddr_storage *addr1, socklen_t addr1_len, @@ -343,6 +345,7 @@ struct sock_addr_test { /* BPF prog properties */ load_fn loadfn; destroy_fn destroyfn; + enum bpf_attach_type attach_type; /* Socket operations */ struct sock_ops *ops; /* Socket properties */ @@ -354,15 +357,34 @@ struct sock_addr_test { const char *expected_addr; unsigned short expected_port; const char *expected_src_addr; + /* Expected test result */ + enum { + LOAD_REJECT, + ATTACH_REJECT, + SYSCALL_EPERM, + SYSCALL_ENOTSUPP, + SUCCESS, + } expected_result; }; #define BPF_SKEL_FUNCS(skel_name, prog_name) \ -static void *prog_name##_load(int cgroup_fd) \ +static void *prog_name##_load(int cgroup_fd, \ + enum bpf_attach_type attach_type, \ + bool expect_reject) \ { \ - struct skel_name *skel; \ - skel = skel_name##__open_and_load(); \ + struct skel_name *skel = skel_name##__open(); \ if (!ASSERT_OK_PTR(skel, "skel_open")) \ goto cleanup; \ + if (!ASSERT_OK(bpf_program__set_expected_attach_type(skel->progs.prog_name, \ + attach_type), \ + "set_expected_attach_type")) \ + goto cleanup; \ + if (skel_name##__load(skel)) { \ + ASSERT_TRUE(expect_reject, "unexpected rejection"); \ + goto cleanup; \ + } \ + if (!ASSERT_FALSE(expect_reject, "expected rejection")) \ + goto cleanup; \ skel->links.prog_name = bpf_program__attach_cgroup( \ skel->progs.prog_name, cgroup_fd); \ if (!ASSERT_OK_PTR(skel->links.prog_name, "prog_attach")) \ @@ -398,6 +420,7 @@ static struct sock_addr_test tests[] = { "bind4: bind (stream)", bind_v4_prog_load, bind_v4_prog_destroy, + BPF_CGROUP_INET4_BIND, &user_ops, AF_INET, SOCK_STREAM, @@ -406,12 +429,14 @@ static struct sock_addr_test tests[] = { SERV4_REWRITE_IP, SERV4_REWRITE_PORT, NULL, + SUCCESS, }, { SOCK_ADDR_TEST_BIND, "bind4: bind (dgram)", bind_v4_prog_load, bind_v4_prog_destroy, + BPF_CGROUP_INET4_BIND, &user_ops, AF_INET, SOCK_DGRAM, @@ -420,12 +445,14 @@ static struct sock_addr_test tests[] = { SERV4_REWRITE_IP, SERV4_REWRITE_PORT, NULL, + SUCCESS, }, { SOCK_ADDR_TEST_BIND, "bind6: bind (stream)", bind_v6_prog_load, bind_v6_prog_destroy, + BPF_CGROUP_INET6_BIND, &user_ops, AF_INET6, SOCK_STREAM, @@ -434,12 +461,14 @@ static struct sock_addr_test tests[] = { SERV6_REWRITE_IP, SERV6_REWRITE_PORT, NULL, + SUCCESS, }, { SOCK_ADDR_TEST_BIND, "bind6: bind (dgram)", bind_v6_prog_load, bind_v6_prog_destroy, + BPF_CGROUP_INET6_BIND, &user_ops, AF_INET6, SOCK_DGRAM, @@ -448,6 +477,7 @@ static struct sock_addr_test tests[] = { SERV6_REWRITE_IP, SERV6_REWRITE_PORT, NULL, + SUCCESS, }, /* bind - kernel calls */ @@ -456,6 +486,7 @@ static struct sock_addr_test tests[] = { "bind4: kernel_bind (stream)", bind_v4_prog_load, bind_v4_prog_destroy, + BPF_CGROUP_INET4_BIND, &kern_ops_sock_sendmsg, AF_INET, SOCK_STREAM, @@ -463,12 +494,15 @@ static struct sock_addr_test tests[] = { SERV4_PORT, SERV4_REWRITE_IP, SERV4_REWRITE_PORT, + NULL, + SUCCESS, }, { SOCK_ADDR_TEST_BIND, "bind4: kernel_bind (dgram)", bind_v4_prog_load, bind_v4_prog_destroy, + BPF_CGROUP_INET4_BIND, &kern_ops_sock_sendmsg, AF_INET, SOCK_DGRAM, @@ -476,12 +510,15 @@ static struct sock_addr_test tests[] = { SERV4_PORT, SERV4_REWRITE_IP, SERV4_REWRITE_PORT, + NULL, + SUCCESS, }, { SOCK_ADDR_TEST_BIND, "bind6: kernel_bind (stream)", bind_v6_prog_load, bind_v6_prog_destroy, + BPF_CGROUP_INET6_BIND, &kern_ops_sock_sendmsg, AF_INET6, SOCK_STREAM, @@ -489,12 +526,15 @@ static struct sock_addr_test tests[] = { SERV6_PORT, SERV6_REWRITE_IP, SERV6_REWRITE_PORT, + NULL, + SUCCESS, }, { SOCK_ADDR_TEST_BIND, "bind6: kernel_bind (dgram)", bind_v6_prog_load, bind_v6_prog_destroy, + BPF_CGROUP_INET6_BIND, &kern_ops_sock_sendmsg, AF_INET6, SOCK_DGRAM, @@ -502,6 +542,8 @@ static struct sock_addr_test tests[] = { SERV6_PORT, SERV6_REWRITE_IP, SERV6_REWRITE_PORT, + NULL, + SUCCESS, }, /* connect - system calls */ @@ -510,6 +552,7 @@ static struct sock_addr_test tests[] = { "connect4: connect (stream)", connect_v4_prog_load, connect_v4_prog_destroy, + BPF_CGROUP_INET4_CONNECT, &user_ops, AF_INET, SOCK_STREAM, @@ -518,12 +561,14 @@ static struct sock_addr_test tests[] = { SERV4_REWRITE_IP, SERV4_REWRITE_PORT, SRC4_REWRITE_IP, + SUCCESS, }, { SOCK_ADDR_TEST_CONNECT, "connect4: connect (dgram)", connect_v4_prog_load, connect_v4_prog_destroy, + BPF_CGROUP_INET4_CONNECT, &user_ops, AF_INET, SOCK_DGRAM, @@ -532,12 +577,14 @@ static struct sock_addr_test tests[] = { SERV4_REWRITE_IP, SERV4_REWRITE_PORT, SRC4_REWRITE_IP, + SUCCESS, }, { SOCK_ADDR_TEST_CONNECT, "connect6: connect (stream)", connect_v6_prog_load, connect_v6_prog_destroy, + BPF_CGROUP_INET6_CONNECT, &user_ops, AF_INET6, SOCK_STREAM, @@ -546,12 +593,14 @@ static struct sock_addr_test tests[] = { SERV6_REWRITE_IP, SERV6_REWRITE_PORT, SRC6_REWRITE_IP, + SUCCESS, }, { SOCK_ADDR_TEST_CONNECT, "connect6: connect (dgram)", connect_v6_prog_load, connect_v6_prog_destroy, + BPF_CGROUP_INET6_CONNECT, &user_ops, AF_INET6, SOCK_DGRAM, @@ -560,12 +609,14 @@ static struct sock_addr_test tests[] = { SERV6_REWRITE_IP, SERV6_REWRITE_PORT, SRC6_REWRITE_IP, + SUCCESS, }, { SOCK_ADDR_TEST_CONNECT, "connect_unix: connect (stream)", connect_unix_prog_load, connect_unix_prog_destroy, + BPF_CGROUP_UNIX_CONNECT, &user_ops, AF_UNIX, SOCK_STREAM, @@ -574,6 +625,7 @@ static struct sock_addr_test tests[] = { SERVUN_REWRITE_ADDRESS, 0, NULL, + SUCCESS, }, /* connect - kernel calls */ @@ -582,6 +634,7 @@ static struct sock_addr_test tests[] = { "connect4: kernel_connect (stream)", connect_v4_prog_load, connect_v4_prog_destroy, + BPF_CGROUP_INET4_CONNECT, &kern_ops_sock_sendmsg, AF_INET, SOCK_STREAM, @@ -590,12 +643,14 @@ static struct sock_addr_test tests[] = { SERV4_REWRITE_IP, SERV4_REWRITE_PORT, SRC4_REWRITE_IP, + SUCCESS, }, { SOCK_ADDR_TEST_CONNECT, "connect4: kernel_connect (dgram)", connect_v4_prog_load, connect_v4_prog_destroy, + BPF_CGROUP_INET4_CONNECT, &kern_ops_sock_sendmsg, AF_INET, SOCK_DGRAM, @@ -604,12 +659,14 @@ static struct sock_addr_test tests[] = { SERV4_REWRITE_IP, SERV4_REWRITE_PORT, SRC4_REWRITE_IP, + SUCCESS, }, { SOCK_ADDR_TEST_CONNECT, "connect6: kernel_connect (stream)", connect_v6_prog_load, connect_v6_prog_destroy, + BPF_CGROUP_INET6_CONNECT, &kern_ops_sock_sendmsg, AF_INET6, SOCK_STREAM, @@ -618,12 +675,14 @@ static struct sock_addr_test tests[] = { SERV6_REWRITE_IP, SERV6_REWRITE_PORT, SRC6_REWRITE_IP, + SUCCESS, }, { SOCK_ADDR_TEST_CONNECT, "connect6: kernel_connect (dgram)", connect_v6_prog_load, connect_v6_prog_destroy, + BPF_CGROUP_INET6_CONNECT, &kern_ops_sock_sendmsg, AF_INET6, SOCK_DGRAM, @@ -632,12 +691,14 @@ static struct sock_addr_test tests[] = { SERV6_REWRITE_IP, SERV6_REWRITE_PORT, SRC6_REWRITE_IP, + SUCCESS, }, { SOCK_ADDR_TEST_CONNECT, "connect_unix: kernel_connect (dgram)", connect_unix_prog_load, connect_unix_prog_destroy, + BPF_CGROUP_UNIX_CONNECT, &kern_ops_sock_sendmsg, AF_UNIX, SOCK_STREAM, @@ -646,6 +707,7 @@ static struct sock_addr_test tests[] = { SERVUN_REWRITE_ADDRESS, 0, NULL, + SUCCESS, }, /* sendmsg - system calls */ @@ -654,6 +716,7 @@ static struct sock_addr_test tests[] = { "sendmsg4: sendmsg (dgram)", sendmsg_v4_prog_load, sendmsg_v4_prog_destroy, + BPF_CGROUP_UDP4_SENDMSG, &user_ops, AF_INET, SOCK_DGRAM, @@ -662,12 +725,14 @@ static struct sock_addr_test tests[] = { SERV4_REWRITE_IP, SERV4_REWRITE_PORT, SRC4_REWRITE_IP, + SUCCESS, }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg6: sendmsg (dgram)", sendmsg_v6_prog_load, sendmsg_v6_prog_destroy, + BPF_CGROUP_UDP6_SENDMSG, &user_ops, AF_INET6, SOCK_DGRAM, @@ -676,12 +741,14 @@ static struct sock_addr_test tests[] = { SERV6_REWRITE_IP, SERV6_REWRITE_PORT, SRC6_REWRITE_IP, + SUCCESS, }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg_unix: sendmsg (dgram)", sendmsg_unix_prog_load, sendmsg_unix_prog_destroy, + BPF_CGROUP_UNIX_SENDMSG, &user_ops, AF_UNIX, SOCK_DGRAM, @@ -690,6 +757,7 @@ static struct sock_addr_test tests[] = { SERVUN_REWRITE_ADDRESS, 0, NULL, + SUCCESS, }, /* sendmsg - kernel calls (sock_sendmsg) */ @@ -698,6 +766,7 @@ static struct sock_addr_test tests[] = { "sendmsg4: sock_sendmsg (dgram)", sendmsg_v4_prog_load, sendmsg_v4_prog_destroy, + BPF_CGROUP_UDP4_SENDMSG, &kern_ops_sock_sendmsg, AF_INET, SOCK_DGRAM, @@ -706,12 +775,14 @@ static struct sock_addr_test tests[] = { SERV4_REWRITE_IP, SERV4_REWRITE_PORT, SRC4_REWRITE_IP, + SUCCESS, }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg6: sock_sendmsg (dgram)", sendmsg_v6_prog_load, sendmsg_v6_prog_destroy, + BPF_CGROUP_UDP6_SENDMSG, &kern_ops_sock_sendmsg, AF_INET6, SOCK_DGRAM, @@ -720,12 +791,14 @@ static struct sock_addr_test tests[] = { SERV6_REWRITE_IP, SERV6_REWRITE_PORT, SRC6_REWRITE_IP, + SUCCESS, }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg_unix: sock_sendmsg (dgram)", sendmsg_unix_prog_load, sendmsg_unix_prog_destroy, + BPF_CGROUP_UNIX_SENDMSG, &kern_ops_sock_sendmsg, AF_UNIX, SOCK_DGRAM, @@ -734,6 +807,7 @@ static struct sock_addr_test tests[] = { SERVUN_REWRITE_ADDRESS, 0, NULL, + SUCCESS, }, /* sendmsg - kernel calls (kernel_sendmsg) */ @@ -742,6 +816,7 @@ static struct sock_addr_test tests[] = { "sendmsg4: kernel_sendmsg (dgram)", sendmsg_v4_prog_load, sendmsg_v4_prog_destroy, + BPF_CGROUP_UDP4_SENDMSG, &kern_ops_kernel_sendmsg, AF_INET, SOCK_DGRAM, @@ -750,12 +825,14 @@ static struct sock_addr_test tests[] = { SERV4_REWRITE_IP, SERV4_REWRITE_PORT, SRC4_REWRITE_IP, + SUCCESS, }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg6: kernel_sendmsg (dgram)", sendmsg_v6_prog_load, sendmsg_v6_prog_destroy, + BPF_CGROUP_UDP6_SENDMSG, &kern_ops_kernel_sendmsg, AF_INET6, SOCK_DGRAM, @@ -764,12 +841,14 @@ static struct sock_addr_test tests[] = { SERV6_REWRITE_IP, SERV6_REWRITE_PORT, SRC6_REWRITE_IP, + SUCCESS, }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg_unix: sock_sendmsg (dgram)", sendmsg_unix_prog_load, sendmsg_unix_prog_destroy, + BPF_CGROUP_UNIX_SENDMSG, &kern_ops_kernel_sendmsg, AF_UNIX, SOCK_DGRAM, @@ -778,6 +857,7 @@ static struct sock_addr_test tests[] = { SERVUN_REWRITE_ADDRESS, 0, NULL, + SUCCESS, }, /* recvmsg - system calls */ @@ -786,6 +866,7 @@ static struct sock_addr_test tests[] = { "recvmsg4: recvfrom (dgram)", recvmsg4_prog_load, recvmsg4_prog_destroy, + BPF_CGROUP_UDP4_RECVMSG, &user_ops, AF_INET, SOCK_DGRAM, @@ -794,12 +875,14 @@ static struct sock_addr_test tests[] = { SERV4_REWRITE_IP, SERV4_REWRITE_PORT, SERV4_IP, + SUCCESS, }, { SOCK_ADDR_TEST_RECVMSG, "recvmsg6: recvfrom (dgram)", recvmsg6_prog_load, recvmsg6_prog_destroy, + BPF_CGROUP_UDP6_RECVMSG, &user_ops, AF_INET6, SOCK_DGRAM, @@ -808,12 +891,14 @@ static struct sock_addr_test tests[] = { SERV6_REWRITE_IP, SERV6_REWRITE_PORT, SERV6_IP, + SUCCESS, }, { SOCK_ADDR_TEST_RECVMSG, "recvmsg_unix: recvfrom (dgram)", recvmsg_unix_prog_load, recvmsg_unix_prog_destroy, + BPF_CGROUP_UNIX_RECVMSG, &user_ops, AF_UNIX, SOCK_DGRAM, @@ -822,12 +907,14 @@ static struct sock_addr_test tests[] = { SERVUN_REWRITE_ADDRESS, 0, SERVUN_ADDRESS, + SUCCESS, }, { SOCK_ADDR_TEST_RECVMSG, "recvmsg_unix: recvfrom (stream)", recvmsg_unix_prog_load, recvmsg_unix_prog_destroy, + BPF_CGROUP_UNIX_RECVMSG, &user_ops, AF_UNIX, SOCK_STREAM, @@ -836,6 +923,7 @@ static struct sock_addr_test tests[] = { SERVUN_REWRITE_ADDRESS, 0, SERVUN_ADDRESS, + SUCCESS, }, /* getsockname - system calls */ @@ -844,6 +932,7 @@ static struct sock_addr_test tests[] = { "getsockname_unix", getsockname_unix_prog_load, getsockname_unix_prog_destroy, + BPF_CGROUP_UNIX_GETSOCKNAME, &user_ops, AF_UNIX, SOCK_STREAM, @@ -852,6 +941,7 @@ static struct sock_addr_test tests[] = { SERVUN_REWRITE_ADDRESS, 0, NULL, + SUCCESS, }, /* getpeername - system calls */ @@ -860,6 +950,7 @@ static struct sock_addr_test tests[] = { "getpeername_unix", getpeername_unix_prog_load, getpeername_unix_prog_destroy, + BPF_CGROUP_UNIX_GETPEERNAME, &user_ops, AF_UNIX, SOCK_STREAM, @@ -868,6 +959,7 @@ static struct sock_addr_test tests[] = { SERVUN_REWRITE_ADDRESS, 0, NULL, + SUCCESS, }, }; @@ -1249,7 +1341,8 @@ void test_sock_addr(void) if (!test__start_subtest(test->name)) continue; - skel = test->loadfn(cgroup_fd); + skel = test->loadfn(cgroup_fd, test->attach_type, + test->expected_result == LOAD_REJECT); if (!skel) continue; From 5a047b2226c0511d4528d1467dc90f08fffafc38 Mon Sep 17 00:00:00 2001 From: Jordan Rife Date: Fri, 10 May 2024 14:02:21 -0500 Subject: [PATCH 04/17] selftests/bpf: Handle ATTACH_REJECT test cases In preparation to move test cases from bpf/test_sock_addr.c that expect ATTACH_REJECT, this patch adds BPF_SKEL_FUNCS_RAW to generate load and destroy functions that use bpf_prog_attach() to control the attach_type. The normal load functions use bpf_program__attach_cgroup which does not have the same degree of control over the attach type, as bpf_program_attach_fd() calls bpf_link_create() with the attach type extracted from prog using bpf_program__expected_attach_type(). It is currently not possible to modify the attach type before bpf_program__attach_cgroup() is called, since bpf_program__set_expected_attach_type() has no effect after the program is loaded. Signed-off-by: Jordan Rife Link: https://lore.kernel.org/r/20240510190246.3247730-5-jrife@google.com Signed-off-by: Alexei Starovoitov --- .../selftests/bpf/prog_tests/sock_addr.c | 35 ++++++++++++++++++- 1 file changed, 34 insertions(+), 1 deletion(-) diff --git a/tools/testing/selftests/bpf/prog_tests/sock_addr.c b/tools/testing/selftests/bpf/prog_tests/sock_addr.c index 3033641fd756..53440458f365 100644 --- a/tools/testing/selftests/bpf/prog_tests/sock_addr.c +++ b/tools/testing/selftests/bpf/prog_tests/sock_addr.c @@ -367,6 +367,38 @@ struct sock_addr_test { } expected_result; }; +#define BPF_SKEL_FUNCS_RAW(skel_name, prog_name) \ +static void *prog_name##_load_raw(int cgroup_fd, \ + enum bpf_attach_type attach_type, \ + bool expect_reject) \ +{ \ + struct skel_name *skel = skel_name##__open(); \ + int prog_fd = -1; \ + if (!ASSERT_OK_PTR(skel, "skel_open")) \ + goto cleanup; \ + if (!ASSERT_OK(skel_name##__load(skel), "load")) \ + goto cleanup; \ + prog_fd = bpf_program__fd(skel->progs.prog_name); \ + if (!ASSERT_GT(prog_fd, 0, "prog_fd")) \ + goto cleanup; \ + if (bpf_prog_attach(prog_fd, cgroup_fd, attach_type, \ + BPF_F_ALLOW_OVERRIDE), "bpf_prog_attach") { \ + ASSERT_TRUE(expect_reject, "unexpected rejection"); \ + goto cleanup; \ + } \ + if (!ASSERT_FALSE(expect_reject, "expected rejection")) \ + goto cleanup; \ +cleanup: \ + if (prog_fd > 0) \ + bpf_prog_detach(cgroup_fd, attach_type); \ + skel_name##__destroy(skel); \ + return NULL; \ +} \ +static void prog_name##_destroy_raw(void *progfd) \ +{ \ + /* No-op. *_load_raw does all cleanup. */ \ +} \ + #define BPF_SKEL_FUNCS(skel_name, prog_name) \ static void *prog_name##_load(int cgroup_fd, \ enum bpf_attach_type attach_type, \ @@ -1342,7 +1374,8 @@ void test_sock_addr(void) continue; skel = test->loadfn(cgroup_fd, test->attach_type, - test->expected_result == LOAD_REJECT); + test->expected_result == LOAD_REJECT || + test->expected_result == ATTACH_REJECT); if (!skel) continue; From a2618c0d854235deaac2325cf8200a55274afa2b Mon Sep 17 00:00:00 2001 From: Jordan Rife Date: Fri, 10 May 2024 14:02:22 -0500 Subject: [PATCH 05/17] selftests/bpf: Handle SYSCALL_EPERM and SYSCALL_ENOTSUPP test cases In preparation to move test cases from bpf/test_sock_addr.c that expect system calls to return ENOTSUPP or EPERM, this patch propagates errno from relevant system calls up to test_sock_addr() where the result can be checked. Signed-off-by: Jordan Rife Link: https://lore.kernel.org/r/20240510190246.3247730-6-jrife@google.com Signed-off-by: Alexei Starovoitov --- .../selftests/bpf/prog_tests/sock_addr.c | 78 ++++++++++++++----- 1 file changed, 58 insertions(+), 20 deletions(-) diff --git a/tools/testing/selftests/bpf/prog_tests/sock_addr.c b/tools/testing/selftests/bpf/prog_tests/sock_addr.c index 53440458f365..626be900a8fd 100644 --- a/tools/testing/selftests/bpf/prog_tests/sock_addr.c +++ b/tools/testing/selftests/bpf/prog_tests/sock_addr.c @@ -19,6 +19,10 @@ #include "getpeername_unix_prog.skel.h" #include "network_helpers.h" +#ifndef ENOTSUPP +# define ENOTSUPP 524 +#endif + #define TEST_NS "sock_addr" #define TEST_IF_PREFIX "test_sock_addr" #define TEST_IPV4 "127.0.0.4" @@ -43,6 +47,8 @@ #define SERVUN_REWRITE_ADDRESS "bpf_cgroup_unix_test_rewrite" #define SRCUN_ADDRESS "bpf_cgroup_unix_test_src" +#define save_errno_do(op) ({ int __save = errno; op; errno = __save; }) + enum sock_addr_test_type { SOCK_ADDR_TEST_BIND, SOCK_ADDR_TEST_CONNECT, @@ -98,6 +104,7 @@ static int run_bpf_prog(const char *prog_name, void *ctx, int ctx_size) goto err; err = topts.retval; + errno = -topts.retval; goto out; err: err = -1; @@ -221,8 +228,7 @@ int kernel_connect_to_addr(int type, const struct sockaddr_storage *addr, sockle "kernel_init_sock")) goto err; - if (!ASSERT_OK(kernel_connect((struct sockaddr *)addr, addrlen), - "kernel_connect")) + if (kernel_connect((struct sockaddr *)addr, addrlen) < 0) goto err; /* Test code expects a "file descriptor" on success. */ @@ -230,7 +236,7 @@ int kernel_connect_to_addr(int type, const struct sockaddr_storage *addr, sockle goto out; err: err = -1; - ASSERT_OK(kernel_close_sock(0), "kernel_close_sock"); + save_errno_do(ASSERT_OK(kernel_close_sock(0), "kernel_close_sock")); out: return err; } @@ -248,8 +254,7 @@ int kernel_start_server(int family, int type, const char *addr_str, __u16 port, if (make_sockaddr(family, addr_str, port, &addr, &addrlen)) goto err; - if (!ASSERT_OK(kernel_bind(0, (struct sockaddr *)&addr, addrlen), - "kernel_bind")) + if (kernel_bind(0, (struct sockaddr *)&addr, addrlen) < 0) goto err; if (type == SOCK_STREAM) { @@ -262,7 +267,7 @@ int kernel_start_server(int family, int type, const char *addr_str, __u16 port, goto out; err: err = -1; - ASSERT_OK(kernel_close_sock(0), "kernel_close_sock"); + save_errno_do(ASSERT_OK(kernel_close_sock(0), "kernel_close_sock")); out: return err; } @@ -1066,7 +1071,7 @@ static void unload_sock_addr_kern(void) sock_addr_kern__destroy(skel); } -static void test_bind(struct sock_addr_test *test) +static int test_bind(struct sock_addr_test *test) { struct sockaddr_storage expected_addr; socklen_t expected_addr_len = sizeof(struct sockaddr_storage); @@ -1075,8 +1080,10 @@ static void test_bind(struct sock_addr_test *test) serv = test->ops->start_server(test->socket_family, test->socket_type, test->requested_addr, test->requested_port, 0); - if (!ASSERT_GE(serv, 0, "start_server")) - goto cleanup; + if (serv < 0) { + err = errno; + goto err; + } err = make_sockaddr(test->socket_family, test->expected_addr, test->expected_port, @@ -1095,13 +1102,17 @@ static void test_bind(struct sock_addr_test *test) goto cleanup; cleanup: + err = 0; +err: if (client != -1) close(client); if (serv != -1) test->ops->close(serv); + + return err; } -static void test_connect(struct sock_addr_test *test) +static int test_connect(struct sock_addr_test *test) { struct sockaddr_storage addr, expected_addr, expected_src_addr; socklen_t addr_len = sizeof(struct sockaddr_storage), @@ -1121,8 +1132,10 @@ static void test_connect(struct sock_addr_test *test) client = test->ops->connect_to_addr(test->socket_type, &addr, addr_len, NULL); - if (!ASSERT_GE(client, 0, "connect_to_addr")) - goto cleanup; + if (client < 0) { + err = errno; + goto err; + } err = make_sockaddr(test->socket_family, test->expected_addr, test->expected_port, &expected_addr, &expected_addr_len); @@ -1149,13 +1162,17 @@ static void test_connect(struct sock_addr_test *test) goto cleanup; } cleanup: + err = 0; +err: if (client != -1) test->ops->close(client); if (serv != -1) close(serv); + + return err; } -static void test_xmsg(struct sock_addr_test *test) +static int test_xmsg(struct sock_addr_test *test) { struct sockaddr_storage addr, src_addr; socklen_t addr_len = sizeof(struct sockaddr_storage), @@ -1196,6 +1213,11 @@ static void test_xmsg(struct sock_addr_test *test) if (test->socket_type == SOCK_DGRAM) { err = test->ops->sendmsg(client, (struct sockaddr *)&addr, addr_len, &data, sizeof(data)); + if (err < 0) { + err = errno; + goto err; + } + if (!ASSERT_EQ(err, sizeof(data), "sendmsg")) goto cleanup; } else { @@ -1245,13 +1267,17 @@ static void test_xmsg(struct sock_addr_test *test) } cleanup: + err = 0; +err: if (client != -1) test->ops->close(client); if (serv != -1) close(serv); + + return err; } -static void test_getsockname(struct sock_addr_test *test) +static int test_getsockname(struct sock_addr_test *test) { struct sockaddr_storage expected_addr; socklen_t expected_addr_len = sizeof(struct sockaddr_storage); @@ -1275,9 +1301,11 @@ static void test_getsockname(struct sock_addr_test *test) cleanup: if (serv != -1) test->ops->close(serv); + + return 0; } -static void test_getpeername(struct sock_addr_test *test) +static int test_getpeername(struct sock_addr_test *test) { struct sockaddr_storage addr, expected_addr; socklen_t addr_len = sizeof(struct sockaddr_storage), @@ -1314,6 +1342,8 @@ cleanup: test->ops->close(client); if (serv != -1) close(serv); + + return 0; } static int setup_test_env(struct nstoken **tok) @@ -1369,6 +1399,7 @@ void test_sock_addr(void) for (size_t i = 0; i < ARRAY_SIZE(tests); ++i) { struct sock_addr_test *test = &tests[i]; + int err; if (!test__start_subtest(test->name)) continue; @@ -1385,26 +1416,33 @@ void test_sock_addr(void) * the future. */ case SOCK_ADDR_TEST_BIND: - test_bind(test); + err = test_bind(test); break; case SOCK_ADDR_TEST_CONNECT: - test_connect(test); + err = test_connect(test); break; case SOCK_ADDR_TEST_SENDMSG: case SOCK_ADDR_TEST_RECVMSG: - test_xmsg(test); + err = test_xmsg(test); break; case SOCK_ADDR_TEST_GETSOCKNAME: - test_getsockname(test); + err = test_getsockname(test); break; case SOCK_ADDR_TEST_GETPEERNAME: - test_getpeername(test); + err = test_getpeername(test); break; default: ASSERT_TRUE(false, "Unknown sock addr test type"); break; } + if (test->expected_result == SYSCALL_EPERM) + ASSERT_EQ(err, EPERM, "socket operation returns EPERM"); + else if (test->expected_result == SYSCALL_ENOTSUPP) + ASSERT_EQ(err, ENOTSUPP, "socket operation returns ENOTSUPP"); + else if (test->expected_result == SUCCESS) + ASSERT_OK(err, "socket operation succeeds"); + test->destroyfn(skel); } From d1b24fcf1c16290ce8cac467be2f7d6773de9da4 Mon Sep 17 00:00:00 2001 From: Jordan Rife Date: Fri, 10 May 2024 14:02:23 -0500 Subject: [PATCH 06/17] selftests/bpf: Migrate WILDCARD_IP test Move wildcard IP sendmsg test case out of bpf/test_sock_addr.c into prog_tests/sock_addr.c. Signed-off-by: Jordan Rife Link: https://lore.kernel.org/r/20240510190246.3247730-7-jrife@google.com Signed-off-by: Alexei Starovoitov --- .../selftests/bpf/prog_tests/sock_addr.c | 50 +++++++++++++++++++ .../selftests/bpf/progs/sendmsg6_prog.c | 6 +++ tools/testing/selftests/bpf/test_sock_addr.c | 20 -------- 3 files changed, 56 insertions(+), 20 deletions(-) diff --git a/tools/testing/selftests/bpf/prog_tests/sock_addr.c b/tools/testing/selftests/bpf/prog_tests/sock_addr.c index 626be900a8fd..37e9ef5a5ae1 100644 --- a/tools/testing/selftests/bpf/prog_tests/sock_addr.c +++ b/tools/testing/selftests/bpf/prog_tests/sock_addr.c @@ -40,6 +40,7 @@ #define SERV6_V4MAPPED_IP "::ffff:192.168.0.4" #define SRC6_IP "::1" #define SRC6_REWRITE_IP TEST_IPV6 +#define WILDCARD6_IP "::" #define SERV6_PORT 6060 #define SERV6_REWRITE_PORT 6666 @@ -443,6 +444,7 @@ BPF_SKEL_FUNCS(connect6_prog, connect_v6_prog); BPF_SKEL_FUNCS(connect_unix_prog, connect_unix_prog); BPF_SKEL_FUNCS(sendmsg4_prog, sendmsg_v4_prog); BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_prog); +BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_preserve_dst_prog); BPF_SKEL_FUNCS(sendmsg_unix_prog, sendmsg_unix_prog); BPF_SKEL_FUNCS(recvmsg4_prog, recvmsg4_prog); BPF_SKEL_FUNCS(recvmsg6_prog, recvmsg6_prog); @@ -780,6 +782,22 @@ static struct sock_addr_test tests[] = { SRC6_REWRITE_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_SENDMSG, + "sendmsg6: sendmsg [::] (BSD'ism) (dgram)", + sendmsg_v6_preserve_dst_prog_load, + sendmsg_v6_preserve_dst_prog_destroy, + BPF_CGROUP_UDP6_SENDMSG, + &user_ops, + AF_INET6, + SOCK_DGRAM, + WILDCARD6_IP, + SERV6_PORT, + SERV6_REWRITE_IP, + SERV6_PORT, + SRC6_IP, + SUCCESS, + }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg_unix: sendmsg (dgram)", @@ -830,6 +848,22 @@ static struct sock_addr_test tests[] = { SRC6_REWRITE_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_SENDMSG, + "sendmsg6: sock_sendmsg [::] (BSD'ism) (dgram)", + sendmsg_v6_preserve_dst_prog_load, + sendmsg_v6_preserve_dst_prog_destroy, + BPF_CGROUP_UDP6_SENDMSG, + &kern_ops_sock_sendmsg, + AF_INET6, + SOCK_DGRAM, + WILDCARD6_IP, + SERV6_PORT, + SERV6_REWRITE_IP, + SERV6_PORT, + SRC6_IP, + SUCCESS, + }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg_unix: sock_sendmsg (dgram)", @@ -880,6 +914,22 @@ static struct sock_addr_test tests[] = { SRC6_REWRITE_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_SENDMSG, + "sendmsg6: kernel_sendmsg [::] (BSD'ism) (dgram)", + sendmsg_v6_preserve_dst_prog_load, + sendmsg_v6_preserve_dst_prog_destroy, + BPF_CGROUP_UDP6_SENDMSG, + &kern_ops_kernel_sendmsg, + AF_INET6, + SOCK_DGRAM, + WILDCARD6_IP, + SERV6_PORT, + SERV6_REWRITE_IP, + SERV6_PORT, + SRC6_IP, + SUCCESS, + }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg_unix: sock_sendmsg (dgram)", diff --git a/tools/testing/selftests/bpf/progs/sendmsg6_prog.c b/tools/testing/selftests/bpf/progs/sendmsg6_prog.c index bf9b46b806f6..03956a654ce5 100644 --- a/tools/testing/selftests/bpf/progs/sendmsg6_prog.c +++ b/tools/testing/selftests/bpf/progs/sendmsg6_prog.c @@ -59,4 +59,10 @@ int sendmsg_v6_prog(struct bpf_sock_addr *ctx) return 1; } +SEC("cgroup/sendmsg6") +int sendmsg_v6_preserve_dst_prog(struct bpf_sock_addr *ctx) +{ + return 1; +} + char _license[] SEC("license") = "GPL"; diff --git a/tools/testing/selftests/bpf/test_sock_addr.c b/tools/testing/selftests/bpf/test_sock_addr.c index 40e33167bec2..ab8ef02c9c55 100644 --- a/tools/testing/selftests/bpf/test_sock_addr.c +++ b/tools/testing/selftests/bpf/test_sock_addr.c @@ -92,7 +92,6 @@ static int bind4_prog_load(const struct sock_addr_test *test); static int bind6_prog_load(const struct sock_addr_test *test); static int connect4_prog_load(const struct sock_addr_test *test); static int connect6_prog_load(const struct sock_addr_test *test); -static int sendmsg_allow_prog_load(const struct sock_addr_test *test); static int sendmsg_deny_prog_load(const struct sock_addr_test *test); static int sendmsg4_rw_asm_prog_load(const struct sock_addr_test *test); static int sendmsg6_rw_asm_prog_load(const struct sock_addr_test *test); @@ -343,20 +342,6 @@ static struct sock_addr_test tests[] = { SRC6_REWRITE_IP, SUCCESS, }, - { - "sendmsg6: preserve dst IP = [::] (BSD'ism)", - sendmsg_allow_prog_load, - BPF_CGROUP_UDP6_SENDMSG, - BPF_CGROUP_UDP6_SENDMSG, - AF_INET6, - SOCK_DGRAM, - WILDCARD6_IP, - SERV6_PORT, - SERV6_REWRITE_IP, - SERV6_PORT, - SRC6_IP, - SUCCESS, - }, { "sendmsg6: deny call", sendmsg_deny_prog_load, @@ -457,11 +442,6 @@ static int xmsg_ret_only_prog_load(const struct sock_addr_test *test, return load_insns(test, insns, ARRAY_SIZE(insns)); } -static int sendmsg_allow_prog_load(const struct sock_addr_test *test) -{ - return xmsg_ret_only_prog_load(test, /*rc*/ 1); -} - static int sendmsg_deny_prog_load(const struct sock_addr_test *test) { return xmsg_ret_only_prog_load(test, /*rc*/ 0); From f46a10483b27cc5a62b45e7e727445de6430e785 Mon Sep 17 00:00:00 2001 From: Jordan Rife Date: Fri, 10 May 2024 14:02:24 -0500 Subject: [PATCH 07/17] selftests/bpf: Migrate sendmsg deny test cases This set of tests checks that sendmsg calls are rejected (return -EPERM) when the sendmsg* hook returns 0. Replace those in bpf/test_sock_addr.c with corresponding tests in prog_tests/sock_addr.c. Signed-off-by: Jordan Rife Link: https://lore.kernel.org/r/20240510190246.3247730-8-jrife@google.com Signed-off-by: Alexei Starovoitov --- .../selftests/bpf/prog_tests/sock_addr.c | 98 +++++++++++++++++++ .../selftests/bpf/progs/sendmsg4_prog.c | 6 ++ .../selftests/bpf/progs/sendmsg6_prog.c | 6 ++ tools/testing/selftests/bpf/test_sock_addr.c | 45 --------- 4 files changed, 110 insertions(+), 45 deletions(-) diff --git a/tools/testing/selftests/bpf/prog_tests/sock_addr.c b/tools/testing/selftests/bpf/prog_tests/sock_addr.c index 37e9ef5a5ae1..634f7a31b35d 100644 --- a/tools/testing/selftests/bpf/prog_tests/sock_addr.c +++ b/tools/testing/selftests/bpf/prog_tests/sock_addr.c @@ -443,7 +443,9 @@ BPF_SKEL_FUNCS(connect4_prog, connect_v4_prog); BPF_SKEL_FUNCS(connect6_prog, connect_v6_prog); BPF_SKEL_FUNCS(connect_unix_prog, connect_unix_prog); BPF_SKEL_FUNCS(sendmsg4_prog, sendmsg_v4_prog); +BPF_SKEL_FUNCS(sendmsg4_prog, sendmsg_v4_deny_prog); BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_prog); +BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_deny_prog); BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_preserve_dst_prog); BPF_SKEL_FUNCS(sendmsg_unix_prog, sendmsg_unix_prog); BPF_SKEL_FUNCS(recvmsg4_prog, recvmsg4_prog); @@ -766,6 +768,22 @@ static struct sock_addr_test tests[] = { SRC4_REWRITE_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_SENDMSG, + "sendmsg4: sendmsg deny (dgram)", + sendmsg_v4_deny_prog_load, + sendmsg_v4_deny_prog_destroy, + BPF_CGROUP_UDP4_SENDMSG, + &user_ops, + AF_INET, + SOCK_DGRAM, + SERV4_IP, + SERV4_PORT, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + SRC4_REWRITE_IP, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg6: sendmsg (dgram)", @@ -798,6 +816,22 @@ static struct sock_addr_test tests[] = { SRC6_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_SENDMSG, + "sendmsg6: sendmsg deny (dgram)", + sendmsg_v6_deny_prog_load, + sendmsg_v6_deny_prog_destroy, + BPF_CGROUP_UDP6_SENDMSG, + &user_ops, + AF_INET6, + SOCK_DGRAM, + SERV6_IP, + SERV6_PORT, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SRC6_REWRITE_IP, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg_unix: sendmsg (dgram)", @@ -832,6 +866,22 @@ static struct sock_addr_test tests[] = { SRC4_REWRITE_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_SENDMSG, + "sendmsg4: sock_sendmsg deny (dgram)", + sendmsg_v4_deny_prog_load, + sendmsg_v4_deny_prog_destroy, + BPF_CGROUP_UDP4_SENDMSG, + &kern_ops_sock_sendmsg, + AF_INET, + SOCK_DGRAM, + SERV4_IP, + SERV4_PORT, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + SRC4_REWRITE_IP, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg6: sock_sendmsg (dgram)", @@ -864,6 +914,22 @@ static struct sock_addr_test tests[] = { SRC6_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_SENDMSG, + "sendmsg6: sock_sendmsg deny (dgram)", + sendmsg_v6_deny_prog_load, + sendmsg_v6_deny_prog_destroy, + BPF_CGROUP_UDP6_SENDMSG, + &kern_ops_sock_sendmsg, + AF_INET6, + SOCK_DGRAM, + SERV6_IP, + SERV6_PORT, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SRC6_REWRITE_IP, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg_unix: sock_sendmsg (dgram)", @@ -898,6 +964,22 @@ static struct sock_addr_test tests[] = { SRC4_REWRITE_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_SENDMSG, + "sendmsg4: kernel_sendmsg deny (dgram)", + sendmsg_v4_deny_prog_load, + sendmsg_v4_deny_prog_destroy, + BPF_CGROUP_UDP4_SENDMSG, + &kern_ops_kernel_sendmsg, + AF_INET, + SOCK_DGRAM, + SERV4_IP, + SERV4_PORT, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + SRC4_REWRITE_IP, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg6: kernel_sendmsg (dgram)", @@ -930,6 +1012,22 @@ static struct sock_addr_test tests[] = { SRC6_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_SENDMSG, + "sendmsg6: kernel_sendmsg deny (dgram)", + sendmsg_v6_deny_prog_load, + sendmsg_v6_deny_prog_destroy, + BPF_CGROUP_UDP6_SENDMSG, + &kern_ops_kernel_sendmsg, + AF_INET6, + SOCK_DGRAM, + SERV6_IP, + SERV6_PORT, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SRC6_REWRITE_IP, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg_unix: sock_sendmsg (dgram)", diff --git a/tools/testing/selftests/bpf/progs/sendmsg4_prog.c b/tools/testing/selftests/bpf/progs/sendmsg4_prog.c index 351e79aef2fa..edc159598a0e 100644 --- a/tools/testing/selftests/bpf/progs/sendmsg4_prog.c +++ b/tools/testing/selftests/bpf/progs/sendmsg4_prog.c @@ -49,4 +49,10 @@ int sendmsg_v4_prog(struct bpf_sock_addr *ctx) return 1; } +SEC("cgroup/sendmsg4") +int sendmsg_v4_deny_prog(struct bpf_sock_addr *ctx) +{ + return 0; +} + char _license[] SEC("license") = "GPL"; diff --git a/tools/testing/selftests/bpf/progs/sendmsg6_prog.c b/tools/testing/selftests/bpf/progs/sendmsg6_prog.c index 03956a654ce5..0c1825cb994d 100644 --- a/tools/testing/selftests/bpf/progs/sendmsg6_prog.c +++ b/tools/testing/selftests/bpf/progs/sendmsg6_prog.c @@ -65,4 +65,10 @@ int sendmsg_v6_preserve_dst_prog(struct bpf_sock_addr *ctx) return 1; } +SEC("cgroup/sendmsg6") +int sendmsg_v6_deny_prog(struct bpf_sock_addr *ctx) +{ + return 0; +} + char _license[] SEC("license") = "GPL"; diff --git a/tools/testing/selftests/bpf/test_sock_addr.c b/tools/testing/selftests/bpf/test_sock_addr.c index ab8ef02c9c55..91d88358090e 100644 --- a/tools/testing/selftests/bpf/test_sock_addr.c +++ b/tools/testing/selftests/bpf/test_sock_addr.c @@ -92,7 +92,6 @@ static int bind4_prog_load(const struct sock_addr_test *test); static int bind6_prog_load(const struct sock_addr_test *test); static int connect4_prog_load(const struct sock_addr_test *test); static int connect6_prog_load(const struct sock_addr_test *test); -static int sendmsg_deny_prog_load(const struct sock_addr_test *test); static int sendmsg4_rw_asm_prog_load(const struct sock_addr_test *test); static int sendmsg6_rw_asm_prog_load(const struct sock_addr_test *test); static int sendmsg6_rw_v4mapped_prog_load(const struct sock_addr_test *test); @@ -258,20 +257,6 @@ static struct sock_addr_test tests[] = { SRC4_REWRITE_IP, SUCCESS, }, - { - "sendmsg4: deny call", - sendmsg_deny_prog_load, - BPF_CGROUP_UDP4_SENDMSG, - BPF_CGROUP_UDP4_SENDMSG, - AF_INET, - SOCK_DGRAM, - SERV4_IP, - SERV4_PORT, - SERV4_REWRITE_IP, - SERV4_REWRITE_PORT, - SRC4_REWRITE_IP, - SYSCALL_EPERM, - }, { "sendmsg6: load prog with wrong expected attach type", sendmsg6_rw_asm_prog_load, @@ -342,20 +327,6 @@ static struct sock_addr_test tests[] = { SRC6_REWRITE_IP, SUCCESS, }, - { - "sendmsg6: deny call", - sendmsg_deny_prog_load, - BPF_CGROUP_UDP6_SENDMSG, - BPF_CGROUP_UDP6_SENDMSG, - AF_INET6, - SOCK_DGRAM, - SERV6_IP, - SERV6_PORT, - SERV6_REWRITE_IP, - SERV6_REWRITE_PORT, - SRC6_REWRITE_IP, - SYSCALL_EPERM, - }, }; static int load_insns(const struct sock_addr_test *test, @@ -431,22 +402,6 @@ static int connect6_prog_load(const struct sock_addr_test *test) return load_path(test, CONNECT6_PROG_PATH); } -static int xmsg_ret_only_prog_load(const struct sock_addr_test *test, - int32_t rc) -{ - struct bpf_insn insns[] = { - /* return rc */ - BPF_MOV64_IMM(BPF_REG_0, rc), - BPF_EXIT_INSN(), - }; - return load_insns(test, insns, ARRAY_SIZE(insns)); -} - -static int sendmsg_deny_prog_load(const struct sock_addr_test *test) -{ - return xmsg_ret_only_prog_load(test, /*rc*/ 0); -} - static int sendmsg4_rw_asm_prog_load(const struct sock_addr_test *test) { struct sockaddr_in dst4_rw_addr; From 54462e8452f139e313e315959e005408cd31a4e6 Mon Sep 17 00:00:00 2001 From: Jordan Rife Date: Fri, 10 May 2024 14:02:25 -0500 Subject: [PATCH 08/17] selftests/bpf: Migrate sendmsg6 v4 mapped address tests Migrate test case from bpf/test_sock_addr.c ensuring that sendmsg returns -ENOTSUPP when sending to an IPv4-mapped IPv6 address to prog_tests/sock_addr.c. Signed-off-by: Jordan Rife Link: https://lore.kernel.org/r/20240510190246.3247730-9-jrife@google.com Signed-off-by: Alexei Starovoitov --- .../selftests/bpf/prog_tests/sock_addr.c | 17 +++++++++++++ .../selftests/bpf/progs/sendmsg6_prog.c | 25 +++++++++++++++++++ tools/testing/selftests/bpf/test_sock_addr.c | 20 --------------- 3 files changed, 42 insertions(+), 20 deletions(-) diff --git a/tools/testing/selftests/bpf/prog_tests/sock_addr.c b/tools/testing/selftests/bpf/prog_tests/sock_addr.c index 634f7a31b35d..f096203171b1 100644 --- a/tools/testing/selftests/bpf/prog_tests/sock_addr.c +++ b/tools/testing/selftests/bpf/prog_tests/sock_addr.c @@ -447,6 +447,7 @@ BPF_SKEL_FUNCS(sendmsg4_prog, sendmsg_v4_deny_prog); BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_prog); BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_deny_prog); BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_preserve_dst_prog); +BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_v4mapped_prog); BPF_SKEL_FUNCS(sendmsg_unix_prog, sendmsg_unix_prog); BPF_SKEL_FUNCS(recvmsg4_prog, recvmsg4_prog); BPF_SKEL_FUNCS(recvmsg6_prog, recvmsg6_prog); @@ -832,6 +833,22 @@ static struct sock_addr_test tests[] = { SRC6_REWRITE_IP, SYSCALL_EPERM, }, + { + SOCK_ADDR_TEST_SENDMSG, + "sendmsg6: sendmsg IPv4-mapped IPv6 (dgram)", + sendmsg_v6_v4mapped_prog_load, + sendmsg_v6_v4mapped_prog_destroy, + BPF_CGROUP_UDP6_SENDMSG, + &user_ops, + AF_INET6, + SOCK_DGRAM, + SERV6_IP, + SERV6_PORT, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SRC6_REWRITE_IP, + SYSCALL_ENOTSUPP, + }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg_unix: sendmsg (dgram)", diff --git a/tools/testing/selftests/bpf/progs/sendmsg6_prog.c b/tools/testing/selftests/bpf/progs/sendmsg6_prog.c index 0c1825cb994d..7611d9e17dd1 100644 --- a/tools/testing/selftests/bpf/progs/sendmsg6_prog.c +++ b/tools/testing/selftests/bpf/progs/sendmsg6_prog.c @@ -20,6 +20,11 @@ #define DST_REWRITE_IP6_2 0 #define DST_REWRITE_IP6_3 1 +#define DST_REWRITE_IP6_V4_MAPPED_0 0 +#define DST_REWRITE_IP6_V4_MAPPED_1 0 +#define DST_REWRITE_IP6_V4_MAPPED_2 0x0000FFFF +#define DST_REWRITE_IP6_V4_MAPPED_3 0xc0a80004 // 192.168.0.4 + #define DST_REWRITE_PORT6 6666 SEC("cgroup/sendmsg6") @@ -59,6 +64,26 @@ int sendmsg_v6_prog(struct bpf_sock_addr *ctx) return 1; } +SEC("cgroup/sendmsg6") +int sendmsg_v6_v4mapped_prog(struct bpf_sock_addr *ctx) +{ + /* Rewrite source. */ + ctx->msg_src_ip6[0] = bpf_htonl(SRC_REWRITE_IP6_0); + ctx->msg_src_ip6[1] = bpf_htonl(SRC_REWRITE_IP6_1); + ctx->msg_src_ip6[2] = bpf_htonl(SRC_REWRITE_IP6_2); + ctx->msg_src_ip6[3] = bpf_htonl(SRC_REWRITE_IP6_3); + + /* Rewrite destination. */ + ctx->user_ip6[0] = bpf_htonl(DST_REWRITE_IP6_V4_MAPPED_0); + ctx->user_ip6[1] = bpf_htonl(DST_REWRITE_IP6_V4_MAPPED_1); + ctx->user_ip6[2] = bpf_htonl(DST_REWRITE_IP6_V4_MAPPED_2); + ctx->user_ip6[3] = bpf_htonl(DST_REWRITE_IP6_V4_MAPPED_3); + + ctx->user_port = bpf_htons(DST_REWRITE_PORT6); + + return 1; +} + SEC("cgroup/sendmsg6") int sendmsg_v6_preserve_dst_prog(struct bpf_sock_addr *ctx) { diff --git a/tools/testing/selftests/bpf/test_sock_addr.c b/tools/testing/selftests/bpf/test_sock_addr.c index 91d88358090e..4ead113753f8 100644 --- a/tools/testing/selftests/bpf/test_sock_addr.c +++ b/tools/testing/selftests/bpf/test_sock_addr.c @@ -94,7 +94,6 @@ static int connect4_prog_load(const struct sock_addr_test *test); static int connect6_prog_load(const struct sock_addr_test *test); static int sendmsg4_rw_asm_prog_load(const struct sock_addr_test *test); static int sendmsg6_rw_asm_prog_load(const struct sock_addr_test *test); -static int sendmsg6_rw_v4mapped_prog_load(const struct sock_addr_test *test); static int sendmsg6_rw_wildcard_prog_load(const struct sock_addr_test *test); static struct sock_addr_test tests[] = { @@ -299,20 +298,6 @@ static struct sock_addr_test tests[] = { SRC6_REWRITE_IP, SUCCESS, }, - { - "sendmsg6: IPv4-mapped IPv6", - sendmsg6_rw_v4mapped_prog_load, - BPF_CGROUP_UDP6_SENDMSG, - BPF_CGROUP_UDP6_SENDMSG, - AF_INET6, - SOCK_DGRAM, - SERV6_IP, - SERV6_PORT, - SERV6_REWRITE_IP, - SERV6_REWRITE_PORT, - SRC6_REWRITE_IP, - SYSCALL_ENOTSUPP, - }, { "sendmsg6: set dst IP = [::] (BSD'ism)", sendmsg6_rw_wildcard_prog_load, @@ -512,11 +497,6 @@ static int sendmsg6_rw_asm_prog_load(const struct sock_addr_test *test) return sendmsg6_rw_dst_asm_prog_load(test, SERV6_REWRITE_IP); } -static int sendmsg6_rw_v4mapped_prog_load(const struct sock_addr_test *test) -{ - return sendmsg6_rw_dst_asm_prog_load(test, SERV6_V4MAPPED_IP); -} - static int sendmsg6_rw_wildcard_prog_load(const struct sock_addr_test *test) { return sendmsg6_rw_dst_asm_prog_load(test, WILDCARD6_IP); From 8eaf8056a44b28a7b198aa699e35854bbec2c452 Mon Sep 17 00:00:00 2001 From: Jordan Rife Date: Fri, 10 May 2024 14:02:26 -0500 Subject: [PATCH 09/17] selftests/bpf: Migrate wildcard destination rewrite test Migrate test case from bpf/test_sock_addr.c ensuring that sendmsg respects when sendmsg6 hooks rewrite the destination IP with the IPv6 wildcard IP, [::]. Signed-off-by: Jordan Rife Link: https://lore.kernel.org/r/20240510190246.3247730-10-jrife@google.com Signed-off-by: Alexei Starovoitov --- .../selftests/bpf/prog_tests/sock_addr.c | 17 ++++++++++++++++ .../selftests/bpf/progs/sendmsg6_prog.c | 20 +++++++++++++++++++ tools/testing/selftests/bpf/test_sock_addr.c | 20 ------------------- 3 files changed, 37 insertions(+), 20 deletions(-) diff --git a/tools/testing/selftests/bpf/prog_tests/sock_addr.c b/tools/testing/selftests/bpf/prog_tests/sock_addr.c index f096203171b1..e3c450d11b9e 100644 --- a/tools/testing/selftests/bpf/prog_tests/sock_addr.c +++ b/tools/testing/selftests/bpf/prog_tests/sock_addr.c @@ -448,6 +448,7 @@ BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_prog); BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_deny_prog); BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_preserve_dst_prog); BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_v4mapped_prog); +BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_wildcard_prog); BPF_SKEL_FUNCS(sendmsg_unix_prog, sendmsg_unix_prog); BPF_SKEL_FUNCS(recvmsg4_prog, recvmsg4_prog); BPF_SKEL_FUNCS(recvmsg6_prog, recvmsg6_prog); @@ -849,6 +850,22 @@ static struct sock_addr_test tests[] = { SRC6_REWRITE_IP, SYSCALL_ENOTSUPP, }, + { + SOCK_ADDR_TEST_SENDMSG, + "sendmsg6: sendmsg dst IP = [::] (BSD'ism) (dgram)", + sendmsg_v6_wildcard_prog_load, + sendmsg_v6_wildcard_prog_destroy, + BPF_CGROUP_UDP6_SENDMSG, + &user_ops, + AF_INET6, + SOCK_DGRAM, + SERV6_IP, + SERV6_PORT, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SRC6_REWRITE_IP, + SUCCESS, + }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg_unix: sendmsg (dgram)", diff --git a/tools/testing/selftests/bpf/progs/sendmsg6_prog.c b/tools/testing/selftests/bpf/progs/sendmsg6_prog.c index 7611d9e17dd1..36a7f960799f 100644 --- a/tools/testing/selftests/bpf/progs/sendmsg6_prog.c +++ b/tools/testing/selftests/bpf/progs/sendmsg6_prog.c @@ -84,6 +84,26 @@ int sendmsg_v6_v4mapped_prog(struct bpf_sock_addr *ctx) return 1; } +SEC("cgroup/sendmsg6") +int sendmsg_v6_wildcard_prog(struct bpf_sock_addr *ctx) +{ + /* Rewrite source. */ + ctx->msg_src_ip6[0] = bpf_htonl(SRC_REWRITE_IP6_0); + ctx->msg_src_ip6[1] = bpf_htonl(SRC_REWRITE_IP6_1); + ctx->msg_src_ip6[2] = bpf_htonl(SRC_REWRITE_IP6_2); + ctx->msg_src_ip6[3] = bpf_htonl(SRC_REWRITE_IP6_3); + + /* Rewrite destination. */ + ctx->user_ip6[0] = bpf_htonl(0); + ctx->user_ip6[1] = bpf_htonl(0); + ctx->user_ip6[2] = bpf_htonl(0); + ctx->user_ip6[3] = bpf_htonl(0); + + ctx->user_port = bpf_htons(DST_REWRITE_PORT6); + + return 1; +} + SEC("cgroup/sendmsg6") int sendmsg_v6_preserve_dst_prog(struct bpf_sock_addr *ctx) { diff --git a/tools/testing/selftests/bpf/test_sock_addr.c b/tools/testing/selftests/bpf/test_sock_addr.c index 4ead113753f8..85fb2a793be5 100644 --- a/tools/testing/selftests/bpf/test_sock_addr.c +++ b/tools/testing/selftests/bpf/test_sock_addr.c @@ -94,7 +94,6 @@ static int connect4_prog_load(const struct sock_addr_test *test); static int connect6_prog_load(const struct sock_addr_test *test); static int sendmsg4_rw_asm_prog_load(const struct sock_addr_test *test); static int sendmsg6_rw_asm_prog_load(const struct sock_addr_test *test); -static int sendmsg6_rw_wildcard_prog_load(const struct sock_addr_test *test); static struct sock_addr_test tests[] = { /* bind */ @@ -298,20 +297,6 @@ static struct sock_addr_test tests[] = { SRC6_REWRITE_IP, SUCCESS, }, - { - "sendmsg6: set dst IP = [::] (BSD'ism)", - sendmsg6_rw_wildcard_prog_load, - BPF_CGROUP_UDP6_SENDMSG, - BPF_CGROUP_UDP6_SENDMSG, - AF_INET6, - SOCK_DGRAM, - SERV6_IP, - SERV6_PORT, - SERV6_REWRITE_IP, - SERV6_REWRITE_PORT, - SRC6_REWRITE_IP, - SUCCESS, - }, }; static int load_insns(const struct sock_addr_test *test, @@ -497,11 +482,6 @@ static int sendmsg6_rw_asm_prog_load(const struct sock_addr_test *test) return sendmsg6_rw_dst_asm_prog_load(test, SERV6_REWRITE_IP); } -static int sendmsg6_rw_wildcard_prog_load(const struct sock_addr_test *test) -{ - return sendmsg6_rw_dst_asm_prog_load(test, WILDCARD6_IP); -} - static int cmp_addr(const struct sockaddr_storage *addr1, const struct sockaddr_storage *addr2, int cmp_port) { From b0f3af0bffefc54650d9fb10810fc2f974365dfd Mon Sep 17 00:00:00 2001 From: Jordan Rife Date: Fri, 10 May 2024 14:02:27 -0500 Subject: [PATCH 10/17] selftests/bpf: Migrate expected_attach_type tests Migrates tests from progs/test_sock_addr.c ensuring that programs fail to load when the expected attach type does not match. Signed-off-by: Jordan Rife Link: https://lore.kernel.org/r/20240510190246.3247730-11-jrife@google.com Signed-off-by: Alexei Starovoitov --- .../selftests/bpf/prog_tests/sock_addr.c | 96 +++++++++++++++++++ tools/testing/selftests/bpf/test_sock_addr.c | 84 ---------------- 2 files changed, 96 insertions(+), 84 deletions(-) diff --git a/tools/testing/selftests/bpf/prog_tests/sock_addr.c b/tools/testing/selftests/bpf/prog_tests/sock_addr.c index e3c450d11b9e..8c7c56f99754 100644 --- a/tools/testing/selftests/bpf/prog_tests/sock_addr.c +++ b/tools/testing/selftests/bpf/prog_tests/sock_addr.c @@ -490,6 +490,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_BIND, + "bind4: load prog with wrong expected attach type", + bind_v4_prog_load, + bind_v4_prog_destroy, + BPF_CGROUP_INET6_BIND, + &user_ops, + AF_INET, + SOCK_STREAM, + NULL, + 0, + NULL, + 0, + NULL, + LOAD_REJECT, + }, { SOCK_ADDR_TEST_BIND, "bind6: bind (stream)", @@ -522,6 +538,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_BIND, + "bind6: load prog with wrong expected attach type", + bind_v6_prog_load, + bind_v6_prog_destroy, + BPF_CGROUP_INET4_BIND, + &user_ops, + AF_INET6, + SOCK_STREAM, + NULL, + 0, + NULL, + 0, + NULL, + LOAD_REJECT, + }, /* bind - kernel calls */ { @@ -622,6 +654,22 @@ static struct sock_addr_test tests[] = { SRC4_REWRITE_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_CONNECT, + "connect4: load prog with wrong expected attach type", + connect_v4_prog_load, + connect_v4_prog_destroy, + BPF_CGROUP_INET6_CONNECT, + &user_ops, + AF_INET, + SOCK_STREAM, + NULL, + 0, + NULL, + 0, + NULL, + LOAD_REJECT, + }, { SOCK_ADDR_TEST_CONNECT, "connect6: connect (stream)", @@ -654,6 +702,22 @@ static struct sock_addr_test tests[] = { SRC6_REWRITE_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_CONNECT, + "connect6: load prog with wrong expected attach type", + connect_v6_prog_load, + connect_v6_prog_destroy, + BPF_CGROUP_INET4_CONNECT, + &user_ops, + AF_INET6, + SOCK_STREAM, + NULL, + 0, + NULL, + 0, + NULL, + LOAD_REJECT, + }, { SOCK_ADDR_TEST_CONNECT, "connect_unix: connect (stream)", @@ -786,6 +850,22 @@ static struct sock_addr_test tests[] = { SRC4_REWRITE_IP, SYSCALL_EPERM, }, + { + SOCK_ADDR_TEST_SENDMSG, + "sendmsg4: load prog with wrong expected attach type", + sendmsg_v4_prog_load, + sendmsg_v4_prog_destroy, + BPF_CGROUP_UDP6_SENDMSG, + &user_ops, + AF_INET, + SOCK_DGRAM, + NULL, + 0, + NULL, + 0, + NULL, + LOAD_REJECT, + }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg6: sendmsg (dgram)", @@ -866,6 +946,22 @@ static struct sock_addr_test tests[] = { SRC6_REWRITE_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_SENDMSG, + "sendmsg6: load prog with wrong expected attach type", + sendmsg_v6_prog_load, + sendmsg_v6_prog_destroy, + BPF_CGROUP_UDP4_SENDMSG, + &user_ops, + AF_INET6, + SOCK_DGRAM, + NULL, + 0, + NULL, + 0, + NULL, + LOAD_REJECT, + }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg_unix: sendmsg (dgram)", diff --git a/tools/testing/selftests/bpf/test_sock_addr.c b/tools/testing/selftests/bpf/test_sock_addr.c index 85fb2a793be5..4ecbc72477f1 100644 --- a/tools/testing/selftests/bpf/test_sock_addr.c +++ b/tools/testing/selftests/bpf/test_sock_addr.c @@ -97,20 +97,6 @@ static int sendmsg6_rw_asm_prog_load(const struct sock_addr_test *test); static struct sock_addr_test tests[] = { /* bind */ - { - "bind4: load prog with wrong expected attach type", - bind4_prog_load, - BPF_CGROUP_INET6_BIND, - BPF_CGROUP_INET4_BIND, - AF_INET, - SOCK_STREAM, - NULL, - 0, - NULL, - 0, - NULL, - LOAD_REJECT, - }, { "bind4: attach prog with wrong attach type", bind4_prog_load, @@ -125,20 +111,6 @@ static struct sock_addr_test tests[] = { NULL, ATTACH_REJECT, }, - { - "bind6: load prog with wrong expected attach type", - bind6_prog_load, - BPF_CGROUP_INET4_BIND, - BPF_CGROUP_INET6_BIND, - AF_INET6, - SOCK_STREAM, - NULL, - 0, - NULL, - 0, - NULL, - LOAD_REJECT, - }, { "bind6: attach prog with wrong attach type", bind6_prog_load, @@ -155,20 +127,6 @@ static struct sock_addr_test tests[] = { }, /* connect */ - { - "connect4: load prog with wrong expected attach type", - connect4_prog_load, - BPF_CGROUP_INET6_CONNECT, - BPF_CGROUP_INET4_CONNECT, - AF_INET, - SOCK_STREAM, - NULL, - 0, - NULL, - 0, - NULL, - LOAD_REJECT, - }, { "connect4: attach prog with wrong attach type", connect4_prog_load, @@ -183,20 +141,6 @@ static struct sock_addr_test tests[] = { NULL, ATTACH_REJECT, }, - { - "connect6: load prog with wrong expected attach type", - connect6_prog_load, - BPF_CGROUP_INET4_CONNECT, - BPF_CGROUP_INET6_CONNECT, - AF_INET6, - SOCK_STREAM, - NULL, - 0, - NULL, - 0, - NULL, - LOAD_REJECT, - }, { "connect6: attach prog with wrong attach type", connect6_prog_load, @@ -213,20 +157,6 @@ static struct sock_addr_test tests[] = { }, /* sendmsg */ - { - "sendmsg4: load prog with wrong expected attach type", - sendmsg4_rw_asm_prog_load, - BPF_CGROUP_UDP6_SENDMSG, - BPF_CGROUP_UDP4_SENDMSG, - AF_INET, - SOCK_DGRAM, - NULL, - 0, - NULL, - 0, - NULL, - LOAD_REJECT, - }, { "sendmsg4: attach prog with wrong attach type", sendmsg4_rw_asm_prog_load, @@ -255,20 +185,6 @@ static struct sock_addr_test tests[] = { SRC4_REWRITE_IP, SUCCESS, }, - { - "sendmsg6: load prog with wrong expected attach type", - sendmsg6_rw_asm_prog_load, - BPF_CGROUP_UDP4_SENDMSG, - BPF_CGROUP_UDP6_SENDMSG, - AF_INET6, - SOCK_DGRAM, - NULL, - 0, - NULL, - 0, - NULL, - LOAD_REJECT, - }, { "sendmsg6: attach prog with wrong attach type", sendmsg6_rw_asm_prog_load, From cded71f595c0c4396acc9657911c5aa2a289a8dc Mon Sep 17 00:00:00 2001 From: Jordan Rife Date: Fri, 10 May 2024 14:02:28 -0500 Subject: [PATCH 11/17] selftests/bpf: Migrate ATTACH_REJECT test cases Migrate test case from bpf/test_sock_addr.c ensuring that program attachment fails when using an inappropriate attach type. Signed-off-by: Jordan Rife Link: https://lore.kernel.org/r/20240510190246.3247730-12-jrife@google.com Signed-off-by: Alexei Starovoitov --- .../selftests/bpf/prog_tests/sock_addr.c | 102 ++++++++++++ tools/testing/selftests/bpf/test_sock_addr.c | 146 ------------------ 2 files changed, 102 insertions(+), 146 deletions(-) diff --git a/tools/testing/selftests/bpf/prog_tests/sock_addr.c b/tools/testing/selftests/bpf/prog_tests/sock_addr.c index 8c7c56f99754..ebd5e58e38c5 100644 --- a/tools/testing/selftests/bpf/prog_tests/sock_addr.c +++ b/tools/testing/selftests/bpf/prog_tests/sock_addr.c @@ -438,13 +438,19 @@ static void prog_name##_destroy(void *skel) \ } BPF_SKEL_FUNCS(bind4_prog, bind_v4_prog); +BPF_SKEL_FUNCS_RAW(bind4_prog, bind_v4_prog); BPF_SKEL_FUNCS(bind6_prog, bind_v6_prog); +BPF_SKEL_FUNCS_RAW(bind6_prog, bind_v6_prog); BPF_SKEL_FUNCS(connect4_prog, connect_v4_prog); +BPF_SKEL_FUNCS_RAW(connect4_prog, connect_v4_prog); BPF_SKEL_FUNCS(connect6_prog, connect_v6_prog); +BPF_SKEL_FUNCS_RAW(connect6_prog, connect_v6_prog); BPF_SKEL_FUNCS(connect_unix_prog, connect_unix_prog); BPF_SKEL_FUNCS(sendmsg4_prog, sendmsg_v4_prog); +BPF_SKEL_FUNCS_RAW(sendmsg4_prog, sendmsg_v4_prog); BPF_SKEL_FUNCS(sendmsg4_prog, sendmsg_v4_deny_prog); BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_prog); +BPF_SKEL_FUNCS_RAW(sendmsg6_prog, sendmsg_v6_prog); BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_deny_prog); BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_preserve_dst_prog); BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_v4mapped_prog); @@ -506,6 +512,22 @@ static struct sock_addr_test tests[] = { NULL, LOAD_REJECT, }, + { + SOCK_ADDR_TEST_BIND, + "bind4: attach prog with wrong attach type", + bind_v4_prog_load_raw, + bind_v4_prog_destroy_raw, + BPF_CGROUP_INET6_BIND, + &user_ops, + AF_INET, + SOCK_STREAM, + NULL, + 0, + NULL, + 0, + NULL, + ATTACH_REJECT, + }, { SOCK_ADDR_TEST_BIND, "bind6: bind (stream)", @@ -554,6 +576,22 @@ static struct sock_addr_test tests[] = { NULL, LOAD_REJECT, }, + { + SOCK_ADDR_TEST_BIND, + "bind6: attach prog with wrong attach type", + bind_v6_prog_load_raw, + bind_v6_prog_destroy_raw, + BPF_CGROUP_INET4_BIND, + &user_ops, + AF_INET, + SOCK_STREAM, + NULL, + 0, + NULL, + 0, + NULL, + ATTACH_REJECT, + }, /* bind - kernel calls */ { @@ -670,6 +708,22 @@ static struct sock_addr_test tests[] = { NULL, LOAD_REJECT, }, + { + SOCK_ADDR_TEST_CONNECT, + "connect4: attach prog with wrong attach type", + connect_v4_prog_load_raw, + connect_v4_prog_destroy_raw, + BPF_CGROUP_INET6_CONNECT, + &user_ops, + AF_INET, + SOCK_STREAM, + NULL, + 0, + NULL, + 0, + NULL, + ATTACH_REJECT, + }, { SOCK_ADDR_TEST_CONNECT, "connect6: connect (stream)", @@ -718,6 +772,22 @@ static struct sock_addr_test tests[] = { NULL, LOAD_REJECT, }, + { + SOCK_ADDR_TEST_CONNECT, + "connect6: attach prog with wrong attach type", + connect_v6_prog_load_raw, + connect_v6_prog_destroy_raw, + BPF_CGROUP_INET4_CONNECT, + &user_ops, + AF_INET, + SOCK_STREAM, + NULL, + 0, + NULL, + 0, + NULL, + ATTACH_REJECT, + }, { SOCK_ADDR_TEST_CONNECT, "connect_unix: connect (stream)", @@ -866,6 +936,22 @@ static struct sock_addr_test tests[] = { NULL, LOAD_REJECT, }, + { + SOCK_ADDR_TEST_SENDMSG, + "sendmsg4: attach prog with wrong attach type", + sendmsg_v4_prog_load_raw, + sendmsg_v4_prog_destroy_raw, + BPF_CGROUP_UDP6_SENDMSG, + &user_ops, + AF_INET, + SOCK_DGRAM, + NULL, + 0, + NULL, + 0, + NULL, + ATTACH_REJECT, + }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg6: sendmsg (dgram)", @@ -962,6 +1048,22 @@ static struct sock_addr_test tests[] = { NULL, LOAD_REJECT, }, + { + SOCK_ADDR_TEST_SENDMSG, + "sendmsg6: attach prog with wrong attach type", + sendmsg_v6_prog_load_raw, + sendmsg_v6_prog_destroy_raw, + BPF_CGROUP_UDP4_SENDMSG, + &user_ops, + AF_INET6, + SOCK_DGRAM, + NULL, + 0, + NULL, + 0, + NULL, + ATTACH_REJECT, + }, { SOCK_ADDR_TEST_SENDMSG, "sendmsg_unix: sendmsg (dgram)", diff --git a/tools/testing/selftests/bpf/test_sock_addr.c b/tools/testing/selftests/bpf/test_sock_addr.c index 4ecbc72477f1..311eda4f4864 100644 --- a/tools/testing/selftests/bpf/test_sock_addr.c +++ b/tools/testing/selftests/bpf/test_sock_addr.c @@ -88,89 +88,11 @@ struct sock_addr_test { } expected_result; }; -static int bind4_prog_load(const struct sock_addr_test *test); -static int bind6_prog_load(const struct sock_addr_test *test); -static int connect4_prog_load(const struct sock_addr_test *test); -static int connect6_prog_load(const struct sock_addr_test *test); static int sendmsg4_rw_asm_prog_load(const struct sock_addr_test *test); static int sendmsg6_rw_asm_prog_load(const struct sock_addr_test *test); static struct sock_addr_test tests[] = { - /* bind */ - { - "bind4: attach prog with wrong attach type", - bind4_prog_load, - BPF_CGROUP_INET4_BIND, - BPF_CGROUP_INET6_BIND, - AF_INET, - SOCK_STREAM, - NULL, - 0, - NULL, - 0, - NULL, - ATTACH_REJECT, - }, - { - "bind6: attach prog with wrong attach type", - bind6_prog_load, - BPF_CGROUP_INET6_BIND, - BPF_CGROUP_INET4_BIND, - AF_INET, - SOCK_STREAM, - NULL, - 0, - NULL, - 0, - NULL, - ATTACH_REJECT, - }, - - /* connect */ - { - "connect4: attach prog with wrong attach type", - connect4_prog_load, - BPF_CGROUP_INET4_CONNECT, - BPF_CGROUP_INET6_CONNECT, - AF_INET, - SOCK_STREAM, - NULL, - 0, - NULL, - 0, - NULL, - ATTACH_REJECT, - }, - { - "connect6: attach prog with wrong attach type", - connect6_prog_load, - BPF_CGROUP_INET6_CONNECT, - BPF_CGROUP_INET4_CONNECT, - AF_INET, - SOCK_STREAM, - NULL, - 0, - NULL, - 0, - NULL, - ATTACH_REJECT, - }, - /* sendmsg */ - { - "sendmsg4: attach prog with wrong attach type", - sendmsg4_rw_asm_prog_load, - BPF_CGROUP_UDP4_SENDMSG, - BPF_CGROUP_UDP6_SENDMSG, - AF_INET, - SOCK_DGRAM, - NULL, - 0, - NULL, - 0, - NULL, - ATTACH_REJECT, - }, { "sendmsg4: rewrite IP & port (asm)", sendmsg4_rw_asm_prog_load, @@ -185,20 +107,6 @@ static struct sock_addr_test tests[] = { SRC4_REWRITE_IP, SUCCESS, }, - { - "sendmsg6: attach prog with wrong attach type", - sendmsg6_rw_asm_prog_load, - BPF_CGROUP_UDP6_SENDMSG, - BPF_CGROUP_UDP4_SENDMSG, - AF_INET6, - SOCK_DGRAM, - NULL, - 0, - NULL, - 0, - NULL, - ATTACH_REJECT, - }, { "sendmsg6: rewrite IP & port (asm)", sendmsg6_rw_asm_prog_load, @@ -234,60 +142,6 @@ static int load_insns(const struct sock_addr_test *test, return ret; } -static int load_path(const struct sock_addr_test *test, const char *path) -{ - struct bpf_object *obj; - struct bpf_program *prog; - int err; - - obj = bpf_object__open_file(path, NULL); - err = libbpf_get_error(obj); - if (err) { - log_err(">>> Opening BPF object (%s) error.\n", path); - return -1; - } - - prog = bpf_object__next_program(obj, NULL); - if (!prog) - goto err_out; - - bpf_program__set_type(prog, BPF_PROG_TYPE_CGROUP_SOCK_ADDR); - bpf_program__set_expected_attach_type(prog, test->expected_attach_type); - bpf_program__set_flags(prog, testing_prog_flags()); - - err = bpf_object__load(obj); - if (err) { - if (test->expected_result != LOAD_REJECT) - log_err(">>> Loading program (%s) error.\n", path); - goto err_out; - } - - return bpf_program__fd(prog); -err_out: - bpf_object__close(obj); - return -1; -} - -static int bind4_prog_load(const struct sock_addr_test *test) -{ - return load_path(test, BIND4_PROG_PATH); -} - -static int bind6_prog_load(const struct sock_addr_test *test) -{ - return load_path(test, BIND6_PROG_PATH); -} - -static int connect4_prog_load(const struct sock_addr_test *test) -{ - return load_path(test, CONNECT4_PROG_PATH); -} - -static int connect6_prog_load(const struct sock_addr_test *test) -{ - return load_path(test, CONNECT6_PROG_PATH); -} - static int sendmsg4_rw_asm_prog_load(const struct sock_addr_test *test) { struct sockaddr_in dst4_rw_addr; From 9c3f17862faef89696d26655a6d10f90137df42e Mon Sep 17 00:00:00 2001 From: Jordan Rife Date: Fri, 10 May 2024 14:02:29 -0500 Subject: [PATCH 12/17] selftests/bpf: Remove redundant sendmsg test cases Remove these test cases completely, as the same behavior is already covered by other sendmsg* test cases in prog_tests/sock_addr.c. This just rewrites the destination address similar to sendmsg_v4_prog and sendmsg_v6_prog. Signed-off-by: Jordan Rife Link: https://lore.kernel.org/r/20240510190246.3247730-13-jrife@google.com Signed-off-by: Alexei Starovoitov --- tools/testing/selftests/bpf/test_sock_addr.c | 161 ------------------- 1 file changed, 161 deletions(-) diff --git a/tools/testing/selftests/bpf/test_sock_addr.c b/tools/testing/selftests/bpf/test_sock_addr.c index 311eda4f4864..a2b587273331 100644 --- a/tools/testing/selftests/bpf/test_sock_addr.c +++ b/tools/testing/selftests/bpf/test_sock_addr.c @@ -88,170 +88,9 @@ struct sock_addr_test { } expected_result; }; -static int sendmsg4_rw_asm_prog_load(const struct sock_addr_test *test); -static int sendmsg6_rw_asm_prog_load(const struct sock_addr_test *test); - static struct sock_addr_test tests[] = { - /* sendmsg */ - { - "sendmsg4: rewrite IP & port (asm)", - sendmsg4_rw_asm_prog_load, - BPF_CGROUP_UDP4_SENDMSG, - BPF_CGROUP_UDP4_SENDMSG, - AF_INET, - SOCK_DGRAM, - SERV4_IP, - SERV4_PORT, - SERV4_REWRITE_IP, - SERV4_REWRITE_PORT, - SRC4_REWRITE_IP, - SUCCESS, - }, - { - "sendmsg6: rewrite IP & port (asm)", - sendmsg6_rw_asm_prog_load, - BPF_CGROUP_UDP6_SENDMSG, - BPF_CGROUP_UDP6_SENDMSG, - AF_INET6, - SOCK_DGRAM, - SERV6_IP, - SERV6_PORT, - SERV6_REWRITE_IP, - SERV6_REWRITE_PORT, - SRC6_REWRITE_IP, - SUCCESS, - }, }; -static int load_insns(const struct sock_addr_test *test, - const struct bpf_insn *insns, size_t insns_cnt) -{ - LIBBPF_OPTS(bpf_prog_load_opts, opts); - int ret; - - opts.expected_attach_type = test->expected_attach_type; - opts.log_buf = bpf_log_buf; - opts.log_size = BPF_LOG_BUF_SIZE; - - ret = bpf_prog_load(BPF_PROG_TYPE_CGROUP_SOCK_ADDR, NULL, "GPL", insns, insns_cnt, &opts); - if (ret < 0 && test->expected_result != LOAD_REJECT) { - log_err(">>> Loading program error.\n" - ">>> Verifier output:\n%s\n-------\n", bpf_log_buf); - } - - return ret; -} - -static int sendmsg4_rw_asm_prog_load(const struct sock_addr_test *test) -{ - struct sockaddr_in dst4_rw_addr; - struct in_addr src4_rw_ip; - - if (inet_pton(AF_INET, SRC4_REWRITE_IP, (void *)&src4_rw_ip) != 1) { - log_err("Invalid IPv4: %s", SRC4_REWRITE_IP); - return -1; - } - - if (make_sockaddr(AF_INET, SERV4_REWRITE_IP, SERV4_REWRITE_PORT, - (struct sockaddr_storage *)&dst4_rw_addr, - NULL) == -1) - return -1; - - struct bpf_insn insns[] = { - BPF_MOV64_REG(BPF_REG_6, BPF_REG_1), - - /* if (sk.family == AF_INET && */ - BPF_LDX_MEM(BPF_W, BPF_REG_7, BPF_REG_6, - offsetof(struct bpf_sock_addr, family)), - BPF_JMP_IMM(BPF_JNE, BPF_REG_7, AF_INET, 8), - - /* sk.type == SOCK_DGRAM) { */ - BPF_LDX_MEM(BPF_W, BPF_REG_7, BPF_REG_6, - offsetof(struct bpf_sock_addr, type)), - BPF_JMP_IMM(BPF_JNE, BPF_REG_7, SOCK_DGRAM, 6), - - /* msg_src_ip4 = src4_rw_ip */ - BPF_MOV32_IMM(BPF_REG_7, src4_rw_ip.s_addr), - BPF_STX_MEM(BPF_W, BPF_REG_6, BPF_REG_7, - offsetof(struct bpf_sock_addr, msg_src_ip4)), - - /* user_ip4 = dst4_rw_addr.sin_addr */ - BPF_MOV32_IMM(BPF_REG_7, dst4_rw_addr.sin_addr.s_addr), - BPF_STX_MEM(BPF_W, BPF_REG_6, BPF_REG_7, - offsetof(struct bpf_sock_addr, user_ip4)), - - /* user_port = dst4_rw_addr.sin_port */ - BPF_MOV32_IMM(BPF_REG_7, dst4_rw_addr.sin_port), - BPF_STX_MEM(BPF_W, BPF_REG_6, BPF_REG_7, - offsetof(struct bpf_sock_addr, user_port)), - /* } */ - - /* return 1 */ - BPF_MOV64_IMM(BPF_REG_0, 1), - BPF_EXIT_INSN(), - }; - - return load_insns(test, insns, ARRAY_SIZE(insns)); -} - -static int sendmsg6_rw_dst_asm_prog_load(const struct sock_addr_test *test, - const char *rw_dst_ip) -{ - struct sockaddr_in6 dst6_rw_addr; - struct in6_addr src6_rw_ip; - - if (inet_pton(AF_INET6, SRC6_REWRITE_IP, (void *)&src6_rw_ip) != 1) { - log_err("Invalid IPv6: %s", SRC6_REWRITE_IP); - return -1; - } - - if (make_sockaddr(AF_INET6, rw_dst_ip, SERV6_REWRITE_PORT, - (struct sockaddr_storage *)&dst6_rw_addr, - NULL) == -1) - return -1; - - struct bpf_insn insns[] = { - BPF_MOV64_REG(BPF_REG_6, BPF_REG_1), - - /* if (sk.family == AF_INET6) { */ - BPF_LDX_MEM(BPF_W, BPF_REG_7, BPF_REG_6, - offsetof(struct bpf_sock_addr, family)), - BPF_JMP_IMM(BPF_JNE, BPF_REG_7, AF_INET6, 18), - -#define STORE_IPV6_WORD_N(DST, SRC, N) \ - BPF_MOV32_IMM(BPF_REG_7, SRC[N]), \ - BPF_STX_MEM(BPF_W, BPF_REG_6, BPF_REG_7, \ - offsetof(struct bpf_sock_addr, DST[N])) - -#define STORE_IPV6(DST, SRC) \ - STORE_IPV6_WORD_N(DST, SRC, 0), \ - STORE_IPV6_WORD_N(DST, SRC, 1), \ - STORE_IPV6_WORD_N(DST, SRC, 2), \ - STORE_IPV6_WORD_N(DST, SRC, 3) - - STORE_IPV6(msg_src_ip6, src6_rw_ip.s6_addr32), - STORE_IPV6(user_ip6, dst6_rw_addr.sin6_addr.s6_addr32), - - /* user_port = dst6_rw_addr.sin6_port */ - BPF_MOV32_IMM(BPF_REG_7, dst6_rw_addr.sin6_port), - BPF_STX_MEM(BPF_W, BPF_REG_6, BPF_REG_7, - offsetof(struct bpf_sock_addr, user_port)), - - /* } */ - - /* return 1 */ - BPF_MOV64_IMM(BPF_REG_0, 1), - BPF_EXIT_INSN(), - }; - - return load_insns(test, insns, ARRAY_SIZE(insns)); -} - -static int sendmsg6_rw_asm_prog_load(const struct sock_addr_test *test) -{ - return sendmsg6_rw_dst_asm_prog_load(test, SERV6_REWRITE_IP); -} - static int cmp_addr(const struct sockaddr_storage *addr1, const struct sockaddr_storage *addr2, int cmp_port) { From 61ecfdfce2647281e7d14119bfa529922ce2d8b2 Mon Sep 17 00:00:00 2001 From: Jordan Rife Date: Fri, 10 May 2024 14:02:30 -0500 Subject: [PATCH 13/17] selftests/bpf: Retire test_sock_addr.(c|sh) Fully remove test_sock_addr.c and test_sock_addr.sh, as test coverage has been fully moved to prog_tests/sock_addr.c. Signed-off-by: Jordan Rife Link: https://lore.kernel.org/r/20240510190246.3247730-14-jrife@google.com Signed-off-by: Alexei Starovoitov --- tools/testing/selftests/bpf/.gitignore | 1 - tools/testing/selftests/bpf/Makefile | 4 +- tools/testing/selftests/bpf/test_sock_addr.c | 574 ------------------ tools/testing/selftests/bpf/test_sock_addr.sh | 58 -- 4 files changed, 1 insertion(+), 636 deletions(-) delete mode 100644 tools/testing/selftests/bpf/test_sock_addr.c delete mode 100755 tools/testing/selftests/bpf/test_sock_addr.sh diff --git a/tools/testing/selftests/bpf/.gitignore b/tools/testing/selftests/bpf/.gitignore index f1aebabfb017..5025401323af 100644 --- a/tools/testing/selftests/bpf/.gitignore +++ b/tools/testing/selftests/bpf/.gitignore @@ -17,7 +17,6 @@ test_dev_cgroup test_verifier_log feature test_sock -test_sock_addr urandom_read test_sockmap test_lirc_mode2_user diff --git a/tools/testing/selftests/bpf/Makefile b/tools/testing/selftests/bpf/Makefile index 135023a357b3..ed381b0197fe 100644 --- a/tools/testing/selftests/bpf/Makefile +++ b/tools/testing/selftests/bpf/Makefile @@ -115,7 +115,6 @@ TEST_PROGS := test_kmod.sh \ test_xdp_redirect_multi.sh \ test_xdp_meta.sh \ test_xdp_veth.sh \ - test_sock_addr.sh \ test_tunnel.sh \ test_lwt_seg6local.sh \ test_lirc_mode2.sh \ @@ -140,7 +139,7 @@ TEST_PROGS_EXTENDED := with_addr.sh \ test_xdp_vlan.sh test_bpftool.py # Compile but not part of 'make run_tests' -TEST_GEN_PROGS_EXTENDED = test_sock_addr test_skb_cgroup_id_user \ +TEST_GEN_PROGS_EXTENDED = test_skb_cgroup_id_user \ flow_dissector_load test_flow_dissector test_tcp_check_syncookie_user \ test_lirc_mode2_user xdping test_cpp runqslower bench bpf_testmod.ko \ xskxceiver xdp_redirect_multi xdp_synproxy veristat xdp_hw_metadata \ @@ -296,7 +295,6 @@ NETWORK_HELPERS := $(OUTPUT)/network_helpers.o $(OUTPUT)/test_dev_cgroup: $(CGROUP_HELPERS) $(TESTING_HELPERS) $(OUTPUT)/test_skb_cgroup_id_user: $(CGROUP_HELPERS) $(TESTING_HELPERS) $(OUTPUT)/test_sock: $(CGROUP_HELPERS) $(TESTING_HELPERS) -$(OUTPUT)/test_sock_addr: $(CGROUP_HELPERS) $(TESTING_HELPERS) $(NETWORK_HELPERS) $(OUTPUT)/test_sockmap: $(CGROUP_HELPERS) $(TESTING_HELPERS) $(OUTPUT)/test_tcpnotify_user: $(CGROUP_HELPERS) $(TESTING_HELPERS) $(TRACE_HELPERS) $(OUTPUT)/get_cgroup_id_user: $(CGROUP_HELPERS) $(TESTING_HELPERS) diff --git a/tools/testing/selftests/bpf/test_sock_addr.c b/tools/testing/selftests/bpf/test_sock_addr.c deleted file mode 100644 index a2b587273331..000000000000 --- a/tools/testing/selftests/bpf/test_sock_addr.c +++ /dev/null @@ -1,574 +0,0 @@ -// SPDX-License-Identifier: GPL-2.0 -// Copyright (c) 2018 Facebook - -#define _GNU_SOURCE - -#include -#include -#include - -#include -#include -#include -#include -#include - -#include - -#include -#include - -#include "cgroup_helpers.h" -#include "network_helpers.h" -#include "testing_helpers.h" -#include "bpf_util.h" - -#ifndef ENOTSUPP -# define ENOTSUPP 524 -#endif - -#define CG_PATH "/foo" -#define CONNECT4_PROG_PATH "./connect4_prog.bpf.o" -#define CONNECT6_PROG_PATH "./connect6_prog.bpf.o" -#define SENDMSG4_PROG_PATH "./sendmsg4_prog.bpf.o" -#define SENDMSG6_PROG_PATH "./sendmsg6_prog.bpf.o" -#define RECVMSG4_PROG_PATH "./recvmsg4_prog.bpf.o" -#define RECVMSG6_PROG_PATH "./recvmsg6_prog.bpf.o" -#define BIND4_PROG_PATH "./bind4_prog.bpf.o" -#define BIND6_PROG_PATH "./bind6_prog.bpf.o" - -#define SERV4_IP "192.168.1.254" -#define SERV4_REWRITE_IP "127.0.0.1" -#define SRC4_IP "172.16.0.1" -#define SRC4_REWRITE_IP "127.0.0.4" -#define SERV4_PORT 4040 -#define SERV4_REWRITE_PORT 4444 - -#define SERV6_IP "face:b00c:1234:5678::abcd" -#define SERV6_REWRITE_IP "::1" -#define SERV6_V4MAPPED_IP "::ffff:192.168.0.4" -#define SRC6_IP "::1" -#define SRC6_REWRITE_IP "::6" -#define WILDCARD6_IP "::" -#define SERV6_PORT 6060 -#define SERV6_REWRITE_PORT 6666 - -#define INET_NTOP_BUF 40 - -struct sock_addr_test; - -typedef int (*load_fn)(const struct sock_addr_test *test); -typedef int (*info_fn)(int, struct sockaddr *, socklen_t *); - -char bpf_log_buf[BPF_LOG_BUF_SIZE]; - -struct sock_addr_test { - const char *descr; - /* BPF prog properties */ - load_fn loadfn; - enum bpf_attach_type expected_attach_type; - enum bpf_attach_type attach_type; - /* Socket properties */ - int domain; - int type; - /* IP:port pairs for BPF prog to override */ - const char *requested_ip; - unsigned short requested_port; - const char *expected_ip; - unsigned short expected_port; - const char *expected_src_ip; - /* Expected test result */ - enum { - LOAD_REJECT, - ATTACH_REJECT, - ATTACH_OKAY, - SYSCALL_EPERM, - SYSCALL_ENOTSUPP, - SUCCESS, - } expected_result; -}; - -static struct sock_addr_test tests[] = { -}; - -static int cmp_addr(const struct sockaddr_storage *addr1, - const struct sockaddr_storage *addr2, int cmp_port) -{ - const struct sockaddr_in *four1, *four2; - const struct sockaddr_in6 *six1, *six2; - - if (addr1->ss_family != addr2->ss_family) - return -1; - - if (addr1->ss_family == AF_INET) { - four1 = (const struct sockaddr_in *)addr1; - four2 = (const struct sockaddr_in *)addr2; - return !((four1->sin_port == four2->sin_port || !cmp_port) && - four1->sin_addr.s_addr == four2->sin_addr.s_addr); - } else if (addr1->ss_family == AF_INET6) { - six1 = (const struct sockaddr_in6 *)addr1; - six2 = (const struct sockaddr_in6 *)addr2; - return !((six1->sin6_port == six2->sin6_port || !cmp_port) && - !memcmp(&six1->sin6_addr, &six2->sin6_addr, - sizeof(struct in6_addr))); - } - - return -1; -} - -static int cmp_sock_addr(info_fn fn, int sock1, - const struct sockaddr_storage *addr2, int cmp_port) -{ - struct sockaddr_storage addr1; - socklen_t len1 = sizeof(addr1); - - memset(&addr1, 0, len1); - if (fn(sock1, (struct sockaddr *)&addr1, (socklen_t *)&len1) != 0) - return -1; - - return cmp_addr(&addr1, addr2, cmp_port); -} - -static int cmp_local_ip(int sock1, const struct sockaddr_storage *addr2) -{ - return cmp_sock_addr(getsockname, sock1, addr2, /*cmp_port*/ 0); -} - -static int cmp_local_addr(int sock1, const struct sockaddr_storage *addr2) -{ - return cmp_sock_addr(getsockname, sock1, addr2, /*cmp_port*/ 1); -} - -static int cmp_peer_addr(int sock1, const struct sockaddr_storage *addr2) -{ - return cmp_sock_addr(getpeername, sock1, addr2, /*cmp_port*/ 1); -} - -int init_pktinfo(int domain, struct cmsghdr *cmsg) -{ - struct in6_pktinfo *pktinfo6; - struct in_pktinfo *pktinfo4; - - if (domain == AF_INET) { - cmsg->cmsg_level = SOL_IP; - cmsg->cmsg_type = IP_PKTINFO; - cmsg->cmsg_len = CMSG_LEN(sizeof(struct in_pktinfo)); - pktinfo4 = (struct in_pktinfo *)CMSG_DATA(cmsg); - memset(pktinfo4, 0, sizeof(struct in_pktinfo)); - if (inet_pton(domain, SRC4_IP, - (void *)&pktinfo4->ipi_spec_dst) != 1) - return -1; - } else if (domain == AF_INET6) { - cmsg->cmsg_level = SOL_IPV6; - cmsg->cmsg_type = IPV6_PKTINFO; - cmsg->cmsg_len = CMSG_LEN(sizeof(struct in6_pktinfo)); - pktinfo6 = (struct in6_pktinfo *)CMSG_DATA(cmsg); - memset(pktinfo6, 0, sizeof(struct in6_pktinfo)); - if (inet_pton(domain, SRC6_IP, - (void *)&pktinfo6->ipi6_addr) != 1) - return -1; - } else { - return -1; - } - - return 0; -} - -static int sendmsg_to_server(int type, const struct sockaddr_storage *addr, - socklen_t addr_len, int set_cmsg, int flags, - int *syscall_err) -{ - union { - char buf[CMSG_SPACE(sizeof(struct in6_pktinfo))]; - struct cmsghdr align; - } control6; - union { - char buf[CMSG_SPACE(sizeof(struct in_pktinfo))]; - struct cmsghdr align; - } control4; - struct msghdr hdr; - struct iovec iov; - char data = 'a'; - int domain; - int fd = -1; - - domain = addr->ss_family; - - if (domain != AF_INET && domain != AF_INET6) { - log_err("Unsupported address family"); - goto err; - } - - fd = socket(domain, type, 0); - if (fd == -1) { - log_err("Failed to create client socket"); - goto err; - } - - memset(&iov, 0, sizeof(iov)); - iov.iov_base = &data; - iov.iov_len = sizeof(data); - - memset(&hdr, 0, sizeof(hdr)); - hdr.msg_name = (void *)addr; - hdr.msg_namelen = addr_len; - hdr.msg_iov = &iov; - hdr.msg_iovlen = 1; - - if (set_cmsg) { - if (domain == AF_INET) { - hdr.msg_control = &control4; - hdr.msg_controllen = sizeof(control4.buf); - } else if (domain == AF_INET6) { - hdr.msg_control = &control6; - hdr.msg_controllen = sizeof(control6.buf); - } - if (init_pktinfo(domain, CMSG_FIRSTHDR(&hdr))) { - log_err("Fail to init pktinfo"); - goto err; - } - } - - if (sendmsg(fd, &hdr, flags) != sizeof(data)) { - log_err("Fail to send message to server"); - *syscall_err = errno; - goto err; - } - - goto out; -err: - close(fd); - fd = -1; -out: - return fd; -} - -static int fastconnect_to_server(const struct sockaddr_storage *addr, - socklen_t addr_len) -{ - int sendmsg_err; - - return sendmsg_to_server(SOCK_STREAM, addr, addr_len, /*set_cmsg*/0, - MSG_FASTOPEN, &sendmsg_err); -} - -static int recvmsg_from_client(int sockfd, struct sockaddr_storage *src_addr) -{ - struct timeval tv; - struct msghdr hdr; - struct iovec iov; - char data[64]; - fd_set rfds; - - FD_ZERO(&rfds); - FD_SET(sockfd, &rfds); - - tv.tv_sec = 2; - tv.tv_usec = 0; - - if (select(sockfd + 1, &rfds, NULL, NULL, &tv) <= 0 || - !FD_ISSET(sockfd, &rfds)) - return -1; - - memset(&iov, 0, sizeof(iov)); - iov.iov_base = data; - iov.iov_len = sizeof(data); - - memset(&hdr, 0, sizeof(hdr)); - hdr.msg_name = src_addr; - hdr.msg_namelen = sizeof(struct sockaddr_storage); - hdr.msg_iov = &iov; - hdr.msg_iovlen = 1; - - return recvmsg(sockfd, &hdr, 0); -} - -static int init_addrs(const struct sock_addr_test *test, - struct sockaddr_storage *requested_addr, - struct sockaddr_storage *expected_addr, - struct sockaddr_storage *expected_src_addr) -{ - if (make_sockaddr(test->domain, test->expected_ip, test->expected_port, - expected_addr, NULL) == -1) - goto err; - - if (make_sockaddr(test->domain, test->requested_ip, test->requested_port, - requested_addr, NULL) == -1) - goto err; - - if (test->expected_src_ip && - make_sockaddr(test->domain, test->expected_src_ip, 0, - expected_src_addr, NULL) == -1) - goto err; - - return 0; -err: - return -1; -} - -static int run_bind_test_case(const struct sock_addr_test *test) -{ - socklen_t addr_len = sizeof(struct sockaddr_storage); - struct sockaddr_storage requested_addr; - struct sockaddr_storage expected_addr; - int clientfd = -1; - int servfd = -1; - int err = 0; - - if (init_addrs(test, &requested_addr, &expected_addr, NULL)) - goto err; - - servfd = start_server_addr(test->type, &requested_addr, addr_len, NULL); - if (servfd == -1) - goto err; - - if (cmp_local_addr(servfd, &expected_addr)) - goto err; - - /* Try to connect to server just in case */ - clientfd = connect_to_addr(test->type, &expected_addr, addr_len, NULL); - if (clientfd == -1) - goto err; - - goto out; -err: - err = -1; -out: - close(clientfd); - close(servfd); - return err; -} - -static int run_connect_test_case(const struct sock_addr_test *test) -{ - socklen_t addr_len = sizeof(struct sockaddr_storage); - struct sockaddr_storage expected_src_addr; - struct sockaddr_storage requested_addr; - struct sockaddr_storage expected_addr; - int clientfd = -1; - int servfd = -1; - int err = 0; - - if (init_addrs(test, &requested_addr, &expected_addr, - &expected_src_addr)) - goto err; - - /* Prepare server to connect to */ - servfd = start_server_addr(test->type, &expected_addr, addr_len, NULL); - if (servfd == -1) - goto err; - - clientfd = connect_to_addr(test->type, &requested_addr, addr_len, NULL); - if (clientfd == -1) - goto err; - - /* Make sure src and dst addrs were overridden properly */ - if (cmp_peer_addr(clientfd, &expected_addr)) - goto err; - - if (cmp_local_ip(clientfd, &expected_src_addr)) - goto err; - - if (test->type == SOCK_STREAM) { - /* Test TCP Fast Open scenario */ - clientfd = fastconnect_to_server(&requested_addr, addr_len); - if (clientfd == -1) - goto err; - - /* Make sure src and dst addrs were overridden properly */ - if (cmp_peer_addr(clientfd, &expected_addr)) - goto err; - - if (cmp_local_ip(clientfd, &expected_src_addr)) - goto err; - } - - goto out; -err: - err = -1; -out: - close(clientfd); - close(servfd); - return err; -} - -static int run_xmsg_test_case(const struct sock_addr_test *test, int max_cmsg) -{ - socklen_t addr_len = sizeof(struct sockaddr_storage); - struct sockaddr_storage expected_addr; - struct sockaddr_storage server_addr; - struct sockaddr_storage sendmsg_addr; - struct sockaddr_storage recvmsg_addr; - int clientfd = -1; - int servfd = -1; - int set_cmsg; - int err = 0; - - if (test->type != SOCK_DGRAM) - goto err; - - if (init_addrs(test, &sendmsg_addr, &server_addr, &expected_addr)) - goto err; - - /* Prepare server to sendmsg to */ - servfd = start_server_addr(test->type, &server_addr, addr_len, NULL); - if (servfd == -1) - goto err; - - for (set_cmsg = 0; set_cmsg <= max_cmsg; ++set_cmsg) { - if (clientfd >= 0) - close(clientfd); - - clientfd = sendmsg_to_server(test->type, &sendmsg_addr, - addr_len, set_cmsg, /*flags*/0, - &err); - if (err) - goto out; - else if (clientfd == -1) - goto err; - - /* Try to receive message on server instead of using - * getpeername(2) on client socket, to check that client's - * destination address was rewritten properly, since - * getpeername(2) doesn't work with unconnected datagram - * sockets. - * - * Get source address from recvmsg(2) as well to make sure - * source was rewritten properly: getsockname(2) can't be used - * since socket is unconnected and source defined for one - * specific packet may differ from the one used by default and - * returned by getsockname(2). - */ - if (recvmsg_from_client(servfd, &recvmsg_addr) == -1) - goto err; - - if (cmp_addr(&recvmsg_addr, &expected_addr, /*cmp_port*/0)) - goto err; - } - - goto out; -err: - err = -1; -out: - close(clientfd); - close(servfd); - return err; -} - -static int run_test_case(int cgfd, const struct sock_addr_test *test) -{ - int progfd = -1; - int err = 0; - - printf("Test case: %s .. ", test->descr); - - progfd = test->loadfn(test); - if (test->expected_result == LOAD_REJECT && progfd < 0) - goto out; - else if (test->expected_result == LOAD_REJECT || progfd < 0) - goto err; - - err = bpf_prog_attach(progfd, cgfd, test->attach_type, - BPF_F_ALLOW_OVERRIDE); - if (test->expected_result == ATTACH_REJECT && err) { - err = 0; /* error was expected, reset it */ - goto out; - } else if (test->expected_result == ATTACH_REJECT || err) { - goto err; - } else if (test->expected_result == ATTACH_OKAY) { - err = 0; - goto out; - } - - switch (test->attach_type) { - case BPF_CGROUP_INET4_BIND: - case BPF_CGROUP_INET6_BIND: - err = run_bind_test_case(test); - break; - case BPF_CGROUP_INET4_CONNECT: - case BPF_CGROUP_INET6_CONNECT: - err = run_connect_test_case(test); - break; - case BPF_CGROUP_UDP4_SENDMSG: - case BPF_CGROUP_UDP6_SENDMSG: - err = run_xmsg_test_case(test, 1); - break; - case BPF_CGROUP_UDP4_RECVMSG: - case BPF_CGROUP_UDP6_RECVMSG: - err = run_xmsg_test_case(test, 0); - break; - default: - goto err; - } - - if (test->expected_result == SYSCALL_EPERM && err == EPERM) { - err = 0; /* error was expected, reset it */ - goto out; - } - - if (test->expected_result == SYSCALL_ENOTSUPP && err == ENOTSUPP) { - err = 0; /* error was expected, reset it */ - goto out; - } - - if (err || test->expected_result != SUCCESS) - goto err; - - goto out; -err: - err = -1; -out: - /* Detaching w/o checking return code: best effort attempt. */ - if (progfd != -1) - bpf_prog_detach(cgfd, test->attach_type); - close(progfd); - printf("[%s]\n", err ? "FAIL" : "PASS"); - return err; -} - -static int run_tests(int cgfd) -{ - int passes = 0; - int fails = 0; - int i; - - for (i = 0; i < ARRAY_SIZE(tests); ++i) { - if (run_test_case(cgfd, &tests[i])) - ++fails; - else - ++passes; - } - printf("Summary: %d PASSED, %d FAILED\n", passes, fails); - return fails ? -1 : 0; -} - -int main(int argc, char **argv) -{ - int cgfd = -1; - int err = 0; - - if (argc < 2) { - fprintf(stderr, - "%s has to be run via %s.sh. Skip direct run.\n", - argv[0], argv[0]); - exit(err); - } - - cgfd = cgroup_setup_and_join(CG_PATH); - if (cgfd < 0) - goto err; - - /* Use libbpf 1.0 API mode */ - libbpf_set_strict_mode(LIBBPF_STRICT_ALL); - - if (run_tests(cgfd)) - goto err; - - goto out; -err: - err = -1; -out: - close(cgfd); - cleanup_cgroup_environment(); - return err; -} diff --git a/tools/testing/selftests/bpf/test_sock_addr.sh b/tools/testing/selftests/bpf/test_sock_addr.sh deleted file mode 100755 index 3b9fdb8094aa..000000000000 --- a/tools/testing/selftests/bpf/test_sock_addr.sh +++ /dev/null @@ -1,58 +0,0 @@ -#!/bin/sh - -set -eu - -ping_once() -{ - type ping${1} >/dev/null 2>&1 && PING="ping${1}" || PING="ping -${1}" - $PING -q -c 1 -W 1 ${2%%/*} >/dev/null 2>&1 -} - -wait_for_ip() -{ - local _i - echo -n "Wait for testing IPv4/IPv6 to become available " - for _i in $(seq ${MAX_PING_TRIES}); do - echo -n "." - if ping_once 4 ${TEST_IPv4} && ping_once 6 ${TEST_IPv6}; then - echo " OK" - return - fi - done - echo 1>&2 "ERROR: Timeout waiting for test IP to become available." - exit 1 -} - -setup() -{ - # Create testing interfaces not to interfere with current environment. - ip link add dev ${TEST_IF} type veth peer name ${TEST_IF_PEER} - ip link set ${TEST_IF} up - ip link set ${TEST_IF_PEER} up - - ip -4 addr add ${TEST_IPv4} dev ${TEST_IF} - ip -6 addr add ${TEST_IPv6} dev ${TEST_IF} - wait_for_ip -} - -cleanup() -{ - ip link del ${TEST_IF} 2>/dev/null || : - ip link del ${TEST_IF_PEER} 2>/dev/null || : -} - -main() -{ - trap cleanup EXIT 2 3 6 15 - setup - ./test_sock_addr setup_done -} - -BASENAME=$(basename $0 .sh) -TEST_IF="${BASENAME}1" -TEST_IF_PEER="${BASENAME}2" -TEST_IPv4="127.0.0.4/8" -TEST_IPv6="::6/128" -MAX_PING_TRIES=5 - -main From 1e0a8367c89f82816735973d0e65a3c8e1b43179 Mon Sep 17 00:00:00 2001 From: Jordan Rife Date: Fri, 10 May 2024 14:02:31 -0500 Subject: [PATCH 14/17] selftests/bpf: Expand sockaddr program return value tests This patch expands verifier coverage for program return values to cover bind, connect, sendmsg, getsockname, and getpeername hooks. It also rounds out the recvmsg coverage by adding test cases for recvmsg_unix hooks. Signed-off-by: Jordan Rife Link: https://lore.kernel.org/r/20240510190246.3247730-15-jrife@google.com Signed-off-by: Alexei Starovoitov --- .../selftests/bpf/progs/verifier_sock_addr.c | 294 ++++++++++++++++++ 1 file changed, 294 insertions(+) diff --git a/tools/testing/selftests/bpf/progs/verifier_sock_addr.c b/tools/testing/selftests/bpf/progs/verifier_sock_addr.c index 5081fa723d3a..9c31448a0f52 100644 --- a/tools/testing/selftests/bpf/progs/verifier_sock_addr.c +++ b/tools/testing/selftests/bpf/progs/verifier_sock_addr.c @@ -34,4 +34,298 @@ int recvmsg6_bad_return_code(struct bpf_sock_addr *ctx) return 0; } +SEC("cgroup/recvmsg_unix") +__success +int recvmsg_unix_good_return_code(struct bpf_sock_addr *ctx) +{ + return 1; +} + +SEC("cgroup/recvmsg_unix") +__failure __msg("At program exit the register R0 has smin=0 smax=0 should have been in [1, 1]") +int recvmsg_unix_bad_return_code(struct bpf_sock_addr *ctx) +{ + return 0; +} + +SEC("cgroup/sendmsg4") +__success +int sendmsg4_good_return_code_0(struct bpf_sock_addr *ctx) +{ + return 0; +} + +SEC("cgroup/sendmsg4") +__success +int sendmsg4_good_return_code_1(struct bpf_sock_addr *ctx) +{ + return 1; +} + +SEC("cgroup/sendmsg4") +__failure __msg("At program exit the register R0 has smin=2 smax=2 should have been in [0, 1]") +int sendmsg4_bad_return_code(struct bpf_sock_addr *ctx) +{ + return 2; +} + +SEC("cgroup/sendmsg6") +__success +int sendmsg6_good_return_code_0(struct bpf_sock_addr *ctx) +{ + return 0; +} + +SEC("cgroup/sendmsg6") +__success +int sendmsg6_good_return_code_1(struct bpf_sock_addr *ctx) +{ + return 1; +} + +SEC("cgroup/sendmsg6") +__failure __msg("At program exit the register R0 has smin=2 smax=2 should have been in [0, 1]") +int sendmsg6_bad_return_code(struct bpf_sock_addr *ctx) +{ + return 2; +} + +SEC("cgroup/sendmsg_unix") +__success +int sendmsg_unix_good_return_code_0(struct bpf_sock_addr *ctx) +{ + return 0; +} + +SEC("cgroup/sendmsg_unix") +__success +int sendmsg_unix_good_return_code_1(struct bpf_sock_addr *ctx) +{ + return 1; +} + +SEC("cgroup/sendmsg_unix") +__failure __msg("At program exit the register R0 has smin=2 smax=2 should have been in [0, 1]") +int sendmsg_unix_bad_return_code(struct bpf_sock_addr *ctx) +{ + return 2; +} + +SEC("cgroup/getpeername4") +__success +int getpeername4_good_return_code(struct bpf_sock_addr *ctx) +{ + return 1; +} + +SEC("cgroup/getpeername4") +__failure __msg("At program exit the register R0 has smin=0 smax=0 should have been in [1, 1]") +int getpeername4_bad_return_code(struct bpf_sock_addr *ctx) +{ + return 0; +} + +SEC("cgroup/getpeername6") +__success +int getpeername6_good_return_code(struct bpf_sock_addr *ctx) +{ + return 1; +} + +SEC("cgroup/getpeername6") +__failure __msg("At program exit the register R0 has smin=0 smax=0 should have been in [1, 1]") +int getpeername6_bad_return_code(struct bpf_sock_addr *ctx) +{ + return 0; +} + +SEC("cgroup/getpeername_unix") +__success +int getpeername_unix_good_return_code(struct bpf_sock_addr *ctx) +{ + return 1; +} + +SEC("cgroup/getpeername_unix") +__failure __msg("At program exit the register R0 has smin=0 smax=0 should have been in [1, 1]") +int getpeername_unix_bad_return_code(struct bpf_sock_addr *ctx) +{ + return 0; +} + +SEC("cgroup/getsockname4") +__success +int getsockname4_good_return_code(struct bpf_sock_addr *ctx) +{ + return 1; +} + +SEC("cgroup/getsockname4") +__failure __msg("At program exit the register R0 has smin=0 smax=0 should have been in [1, 1]") +int getsockname4_bad_return_code(struct bpf_sock_addr *ctx) +{ + return 0; +} + +SEC("cgroup/getsockname6") +__success +int getsockname6_good_return_code(struct bpf_sock_addr *ctx) +{ + return 1; +} + +SEC("cgroup/getsockname6") +__failure __msg("At program exit the register R0 has smin=0 smax=0 should have been in [1, 1]") +int getsockname6_bad_return_code(struct bpf_sock_addr *ctx) +{ + return 0; +} + +SEC("cgroup/getsockname_unix") +__success +int getsockname_unix_good_return_code(struct bpf_sock_addr *ctx) +{ + return 1; +} + +SEC("cgroup/getsockname_unix") +__failure __msg("At program exit the register R0 has smin=0 smax=0 should have been in [1, 1]") +int getsockname_unix_unix_bad_return_code(struct bpf_sock_addr *ctx) +{ + return 0; +} + +SEC("cgroup/bind4") +__success +int bind4_good_return_code_0(struct bpf_sock_addr *ctx) +{ + return 0; +} + +SEC("cgroup/bind4") +__success +int bind4_good_return_code_1(struct bpf_sock_addr *ctx) +{ + return 1; +} + +SEC("cgroup/bind4") +__success +int bind4_good_return_code_2(struct bpf_sock_addr *ctx) +{ + return 2; +} + +SEC("cgroup/bind4") +__success +int bind4_good_return_code_3(struct bpf_sock_addr *ctx) +{ + return 3; +} + +SEC("cgroup/bind4") +__failure __msg("At program exit the register R0 has smin=4 smax=4 should have been in [0, 3]") +int bind4_bad_return_code(struct bpf_sock_addr *ctx) +{ + return 4; +} + +SEC("cgroup/bind6") +__success +int bind6_good_return_code_0(struct bpf_sock_addr *ctx) +{ + return 0; +} + +SEC("cgroup/bind6") +__success +int bind6_good_return_code_1(struct bpf_sock_addr *ctx) +{ + return 1; +} + +SEC("cgroup/bind6") +__success +int bind6_good_return_code_2(struct bpf_sock_addr *ctx) +{ + return 2; +} + +SEC("cgroup/bind6") +__success +int bind6_good_return_code_3(struct bpf_sock_addr *ctx) +{ + return 3; +} + +SEC("cgroup/bind6") +__failure __msg("At program exit the register R0 has smin=4 smax=4 should have been in [0, 3]") +int bind6_bad_return_code(struct bpf_sock_addr *ctx) +{ + return 4; +} + +SEC("cgroup/connect4") +__success +int connect4_good_return_code_0(struct bpf_sock_addr *ctx) +{ + return 0; +} + +SEC("cgroup/connect4") +__success +int connect4_good_return_code_1(struct bpf_sock_addr *ctx) +{ + return 1; +} + +SEC("cgroup/connect4") +__failure __msg("At program exit the register R0 has smin=2 smax=2 should have been in [0, 1]") +int connect4_bad_return_code(struct bpf_sock_addr *ctx) +{ + return 2; +} + +SEC("cgroup/connect6") +__success +int connect6_good_return_code_0(struct bpf_sock_addr *ctx) +{ + return 0; +} + +SEC("cgroup/connect6") +__success +int connect6_good_return_code_1(struct bpf_sock_addr *ctx) +{ + return 1; +} + +SEC("cgroup/connect6") +__failure __msg("At program exit the register R0 has smin=2 smax=2 should have been in [0, 1]") +int connect6_bad_return_code(struct bpf_sock_addr *ctx) +{ + return 2; +} + +SEC("cgroup/connect_unix") +__success +int connect_unix_good_return_code_0(struct bpf_sock_addr *ctx) +{ + return 0; +} + +SEC("cgroup/connect_unix") +__success +int connect_unix_good_return_code_1(struct bpf_sock_addr *ctx) +{ + return 1; +} + +SEC("cgroup/connect_unix") +__failure __msg("At program exit the register R0 has smin=2 smax=2 should have been in [0, 1]") +int connect_unix_bad_return_code(struct bpf_sock_addr *ctx) +{ + return 2; +} + char _license[] SEC("license") = "GPL"; From dfb7539b47b501ccc0d23bae718500ada2157aee Mon Sep 17 00:00:00 2001 From: Jordan Rife Date: Fri, 10 May 2024 14:02:32 -0500 Subject: [PATCH 15/17] sefltests/bpf: Expand sockaddr hook deny tests This patch expands test coverage for EPERM tests to include connect and bind calls and rounds out the coverage for sendmsg by adding tests for sendmsg_unix. Signed-off-by: Jordan Rife Link: https://lore.kernel.org/r/20240510190246.3247730-16-jrife@google.com Signed-off-by: Alexei Starovoitov --- .../selftests/bpf/prog_tests/sock_addr.c | 342 ++++++++++++++++++ .../testing/selftests/bpf/progs/bind4_prog.c | 6 + .../testing/selftests/bpf/progs/bind6_prog.c | 6 + .../selftests/bpf/progs/connect4_prog.c | 6 + .../selftests/bpf/progs/connect6_prog.c | 6 + .../selftests/bpf/progs/connect_unix_prog.c | 6 + .../selftests/bpf/progs/sendmsg_unix_prog.c | 6 + 7 files changed, 378 insertions(+) diff --git a/tools/testing/selftests/bpf/prog_tests/sock_addr.c b/tools/testing/selftests/bpf/prog_tests/sock_addr.c index ebd5e58e38c5..0477b4080b2e 100644 --- a/tools/testing/selftests/bpf/prog_tests/sock_addr.c +++ b/tools/testing/selftests/bpf/prog_tests/sock_addr.c @@ -439,13 +439,18 @@ static void prog_name##_destroy(void *skel) \ BPF_SKEL_FUNCS(bind4_prog, bind_v4_prog); BPF_SKEL_FUNCS_RAW(bind4_prog, bind_v4_prog); +BPF_SKEL_FUNCS(bind4_prog, bind_v4_deny_prog); BPF_SKEL_FUNCS(bind6_prog, bind_v6_prog); BPF_SKEL_FUNCS_RAW(bind6_prog, bind_v6_prog); +BPF_SKEL_FUNCS(bind6_prog, bind_v6_deny_prog); BPF_SKEL_FUNCS(connect4_prog, connect_v4_prog); BPF_SKEL_FUNCS_RAW(connect4_prog, connect_v4_prog); +BPF_SKEL_FUNCS(connect4_prog, connect_v4_deny_prog); BPF_SKEL_FUNCS(connect6_prog, connect_v6_prog); BPF_SKEL_FUNCS_RAW(connect6_prog, connect_v6_prog); +BPF_SKEL_FUNCS(connect6_prog, connect_v6_deny_prog); BPF_SKEL_FUNCS(connect_unix_prog, connect_unix_prog); +BPF_SKEL_FUNCS(connect_unix_prog, connect_unix_deny_prog); BPF_SKEL_FUNCS(sendmsg4_prog, sendmsg_v4_prog); BPF_SKEL_FUNCS_RAW(sendmsg4_prog, sendmsg_v4_prog); BPF_SKEL_FUNCS(sendmsg4_prog, sendmsg_v4_deny_prog); @@ -456,6 +461,7 @@ BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_preserve_dst_prog); BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_v4mapped_prog); BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_wildcard_prog); BPF_SKEL_FUNCS(sendmsg_unix_prog, sendmsg_unix_prog); +BPF_SKEL_FUNCS(sendmsg_unix_prog, sendmsg_unix_deny_prog); BPF_SKEL_FUNCS(recvmsg4_prog, recvmsg4_prog); BPF_SKEL_FUNCS(recvmsg6_prog, recvmsg6_prog); BPF_SKEL_FUNCS(recvmsg_unix_prog, recvmsg_unix_prog); @@ -480,6 +486,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_BIND, + "bind4: bind deny (stream)", + bind_v4_deny_prog_load, + bind_v4_deny_prog_destroy, + BPF_CGROUP_INET4_BIND, + &user_ops, + AF_INET, + SOCK_STREAM, + SERV4_IP, + SERV4_PORT, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + NULL, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_BIND, "bind4: bind (dgram)", @@ -496,6 +518,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_BIND, + "bind4: bind deny (dgram)", + bind_v4_deny_prog_load, + bind_v4_deny_prog_destroy, + BPF_CGROUP_INET4_BIND, + &user_ops, + AF_INET, + SOCK_DGRAM, + SERV4_IP, + SERV4_PORT, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + NULL, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_BIND, "bind4: load prog with wrong expected attach type", @@ -544,6 +582,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_BIND, + "bind6: bind deny (stream)", + bind_v6_deny_prog_load, + bind_v6_deny_prog_destroy, + BPF_CGROUP_INET6_BIND, + &user_ops, + AF_INET6, + SOCK_STREAM, + SERV6_IP, + SERV6_PORT, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + NULL, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_BIND, "bind6: bind (dgram)", @@ -560,6 +614,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_BIND, + "bind6: bind deny (dgram)", + bind_v6_deny_prog_load, + bind_v6_deny_prog_destroy, + BPF_CGROUP_INET6_BIND, + &user_ops, + AF_INET6, + SOCK_DGRAM, + SERV6_IP, + SERV6_PORT, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + NULL, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_BIND, "bind6: load prog with wrong expected attach type", @@ -610,6 +680,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_BIND, + "bind4: kernel_bind deny (stream)", + bind_v4_deny_prog_load, + bind_v4_deny_prog_destroy, + BPF_CGROUP_INET4_BIND, + &kern_ops_sock_sendmsg, + AF_INET, + SOCK_STREAM, + SERV4_IP, + SERV4_PORT, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + NULL, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_BIND, "bind4: kernel_bind (dgram)", @@ -626,6 +712,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_BIND, + "bind4: kernel_bind deny (dgram)", + bind_v4_deny_prog_load, + bind_v4_deny_prog_destroy, + BPF_CGROUP_INET4_BIND, + &kern_ops_sock_sendmsg, + AF_INET, + SOCK_DGRAM, + SERV4_IP, + SERV4_PORT, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + NULL, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_BIND, "bind6: kernel_bind (stream)", @@ -642,6 +744,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_BIND, + "bind6: kernel_bind deny (stream)", + bind_v6_deny_prog_load, + bind_v6_deny_prog_destroy, + BPF_CGROUP_INET6_BIND, + &kern_ops_sock_sendmsg, + AF_INET6, + SOCK_STREAM, + SERV6_IP, + SERV6_PORT, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + NULL, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_BIND, "bind6: kernel_bind (dgram)", @@ -658,6 +776,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_BIND, + "bind6: kernel_bind deny (dgram)", + bind_v6_deny_prog_load, + bind_v6_deny_prog_destroy, + BPF_CGROUP_INET6_BIND, + &kern_ops_sock_sendmsg, + AF_INET6, + SOCK_DGRAM, + SERV6_IP, + SERV6_PORT, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + NULL, + SYSCALL_EPERM, + }, /* connect - system calls */ { @@ -676,6 +810,22 @@ static struct sock_addr_test tests[] = { SRC4_REWRITE_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_CONNECT, + "connect4: connect deny (stream)", + connect_v4_deny_prog_load, + connect_v4_deny_prog_destroy, + BPF_CGROUP_INET4_CONNECT, + &user_ops, + AF_INET, + SOCK_STREAM, + SERV4_IP, + SERV4_PORT, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + SRC4_REWRITE_IP, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_CONNECT, "connect4: connect (dgram)", @@ -692,6 +842,22 @@ static struct sock_addr_test tests[] = { SRC4_REWRITE_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_CONNECT, + "connect4: connect deny (dgram)", + connect_v4_deny_prog_load, + connect_v4_deny_prog_destroy, + BPF_CGROUP_INET4_CONNECT, + &user_ops, + AF_INET, + SOCK_DGRAM, + SERV4_IP, + SERV4_PORT, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + SRC4_REWRITE_IP, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_CONNECT, "connect4: load prog with wrong expected attach type", @@ -740,6 +906,22 @@ static struct sock_addr_test tests[] = { SRC6_REWRITE_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_CONNECT, + "connect6: connect deny (stream)", + connect_v6_deny_prog_load, + connect_v6_deny_prog_destroy, + BPF_CGROUP_INET6_CONNECT, + &user_ops, + AF_INET6, + SOCK_STREAM, + SERV6_IP, + SERV6_PORT, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SRC6_REWRITE_IP, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_CONNECT, "connect6: connect (dgram)", @@ -756,6 +938,22 @@ static struct sock_addr_test tests[] = { SRC6_REWRITE_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_CONNECT, + "connect6: connect deny (dgram)", + connect_v6_deny_prog_load, + connect_v6_deny_prog_destroy, + BPF_CGROUP_INET6_CONNECT, + &user_ops, + AF_INET6, + SOCK_DGRAM, + SERV6_IP, + SERV6_PORT, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SRC6_REWRITE_IP, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_CONNECT, "connect6: load prog with wrong expected attach type", @@ -804,6 +1002,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_CONNECT, + "connect_unix: connect deny (stream)", + connect_unix_deny_prog_load, + connect_unix_deny_prog_destroy, + BPF_CGROUP_UNIX_CONNECT, + &user_ops, + AF_UNIX, + SOCK_STREAM, + SERVUN_ADDRESS, + 0, + SERVUN_REWRITE_ADDRESS, + 0, + NULL, + SYSCALL_EPERM, + }, /* connect - kernel calls */ { @@ -822,6 +1036,22 @@ static struct sock_addr_test tests[] = { SRC4_REWRITE_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_CONNECT, + "connect4: kernel_connect deny (stream)", + connect_v4_deny_prog_load, + connect_v4_deny_prog_destroy, + BPF_CGROUP_INET4_CONNECT, + &kern_ops_sock_sendmsg, + AF_INET, + SOCK_STREAM, + SERV4_IP, + SERV4_PORT, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + SRC4_REWRITE_IP, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_CONNECT, "connect4: kernel_connect (dgram)", @@ -838,6 +1068,22 @@ static struct sock_addr_test tests[] = { SRC4_REWRITE_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_CONNECT, + "connect4: kernel_connect deny (dgram)", + connect_v4_deny_prog_load, + connect_v4_deny_prog_destroy, + BPF_CGROUP_INET4_CONNECT, + &kern_ops_sock_sendmsg, + AF_INET, + SOCK_DGRAM, + SERV4_IP, + SERV4_PORT, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + SRC4_REWRITE_IP, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_CONNECT, "connect6: kernel_connect (stream)", @@ -854,6 +1100,22 @@ static struct sock_addr_test tests[] = { SRC6_REWRITE_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_CONNECT, + "connect6: kernel_connect deny (stream)", + connect_v6_deny_prog_load, + connect_v6_deny_prog_destroy, + BPF_CGROUP_INET6_CONNECT, + &kern_ops_sock_sendmsg, + AF_INET6, + SOCK_STREAM, + SERV6_IP, + SERV6_PORT, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SRC6_REWRITE_IP, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_CONNECT, "connect6: kernel_connect (dgram)", @@ -870,6 +1132,22 @@ static struct sock_addr_test tests[] = { SRC6_REWRITE_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_CONNECT, + "connect6: kernel_connect deny (dgram)", + connect_v6_deny_prog_load, + connect_v6_deny_prog_destroy, + BPF_CGROUP_INET6_CONNECT, + &kern_ops_sock_sendmsg, + AF_INET6, + SOCK_DGRAM, + SERV6_IP, + SERV6_PORT, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SRC6_REWRITE_IP, + SYSCALL_EPERM, + }, { SOCK_ADDR_TEST_CONNECT, "connect_unix: kernel_connect (dgram)", @@ -886,6 +1164,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_CONNECT, + "connect_unix: kernel_connect deny (dgram)", + connect_unix_deny_prog_load, + connect_unix_deny_prog_destroy, + BPF_CGROUP_UNIX_CONNECT, + &kern_ops_sock_sendmsg, + AF_UNIX, + SOCK_STREAM, + SERVUN_ADDRESS, + 0, + SERVUN_REWRITE_ADDRESS, + 0, + NULL, + SYSCALL_EPERM, + }, /* sendmsg - system calls */ { @@ -1080,6 +1374,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_SENDMSG, + "sendmsg_unix: sendmsg deny (dgram)", + sendmsg_unix_deny_prog_load, + sendmsg_unix_deny_prog_destroy, + BPF_CGROUP_UNIX_SENDMSG, + &user_ops, + AF_UNIX, + SOCK_DGRAM, + SERVUN_ADDRESS, + 0, + SERVUN_REWRITE_ADDRESS, + 0, + NULL, + SYSCALL_EPERM, + }, /* sendmsg - kernel calls (sock_sendmsg) */ { @@ -1178,6 +1488,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_SENDMSG, + "sendmsg_unix: sock_sendmsg deny (dgram)", + sendmsg_unix_deny_prog_load, + sendmsg_unix_deny_prog_destroy, + BPF_CGROUP_UNIX_SENDMSG, + &kern_ops_sock_sendmsg, + AF_UNIX, + SOCK_DGRAM, + SERVUN_ADDRESS, + 0, + SERVUN_REWRITE_ADDRESS, + 0, + NULL, + SYSCALL_EPERM, + }, /* sendmsg - kernel calls (kernel_sendmsg) */ { @@ -1276,6 +1602,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_SENDMSG, + "sendmsg_unix: kernel_sendmsg deny (dgram)", + sendmsg_unix_deny_prog_load, + sendmsg_unix_deny_prog_destroy, + BPF_CGROUP_UNIX_SENDMSG, + &kern_ops_kernel_sendmsg, + AF_UNIX, + SOCK_DGRAM, + SERVUN_ADDRESS, + 0, + SERVUN_REWRITE_ADDRESS, + 0, + NULL, + SYSCALL_EPERM, + }, /* recvmsg - system calls */ { diff --git a/tools/testing/selftests/bpf/progs/bind4_prog.c b/tools/testing/selftests/bpf/progs/bind4_prog.c index 66005c1a5b36..b7ddf8ec4ee8 100644 --- a/tools/testing/selftests/bpf/progs/bind4_prog.c +++ b/tools/testing/selftests/bpf/progs/bind4_prog.c @@ -158,4 +158,10 @@ int bind_v4_prog(struct bpf_sock_addr *ctx) return 1; } +SEC("cgroup/bind4") +int bind_v4_deny_prog(struct bpf_sock_addr *ctx) +{ + return 0; +} + char _license[] SEC("license") = "GPL"; diff --git a/tools/testing/selftests/bpf/progs/bind6_prog.c b/tools/testing/selftests/bpf/progs/bind6_prog.c index 9c86c712348c..501c3fc11d35 100644 --- a/tools/testing/selftests/bpf/progs/bind6_prog.c +++ b/tools/testing/selftests/bpf/progs/bind6_prog.c @@ -175,4 +175,10 @@ int bind_v6_prog(struct bpf_sock_addr *ctx) return 1; } +SEC("cgroup/bind6") +int bind_v6_deny_prog(struct bpf_sock_addr *ctx) +{ + return 0; +} + char _license[] SEC("license") = "GPL"; diff --git a/tools/testing/selftests/bpf/progs/connect4_prog.c b/tools/testing/selftests/bpf/progs/connect4_prog.c index bec529da7c9d..9e9ebf27b878 100644 --- a/tools/testing/selftests/bpf/progs/connect4_prog.c +++ b/tools/testing/selftests/bpf/progs/connect4_prog.c @@ -199,4 +199,10 @@ int connect_v4_prog(struct bpf_sock_addr *ctx) return do_bind(ctx) ? 1 : 0; } +SEC("cgroup/connect4") +int connect_v4_deny_prog(struct bpf_sock_addr *ctx) +{ + return 0; +} + char _license[] SEC("license") = "GPL"; diff --git a/tools/testing/selftests/bpf/progs/connect6_prog.c b/tools/testing/selftests/bpf/progs/connect6_prog.c index 40266d2c737c..e98573b00ddb 100644 --- a/tools/testing/selftests/bpf/progs/connect6_prog.c +++ b/tools/testing/selftests/bpf/progs/connect6_prog.c @@ -90,4 +90,10 @@ int connect_v6_prog(struct bpf_sock_addr *ctx) return 1; } +SEC("cgroup/connect6") +int connect_v6_deny_prog(struct bpf_sock_addr *ctx) +{ + return 0; +} + char _license[] SEC("license") = "GPL"; diff --git a/tools/testing/selftests/bpf/progs/connect_unix_prog.c b/tools/testing/selftests/bpf/progs/connect_unix_prog.c index 2ef0e0c46d17..ba60adadb335 100644 --- a/tools/testing/selftests/bpf/progs/connect_unix_prog.c +++ b/tools/testing/selftests/bpf/progs/connect_unix_prog.c @@ -36,4 +36,10 @@ int connect_unix_prog(struct bpf_sock_addr *ctx) return 1; } +SEC("cgroup/connect_unix") +int connect_unix_deny_prog(struct bpf_sock_addr *ctx) +{ + return 0; +} + char _license[] SEC("license") = "GPL"; diff --git a/tools/testing/selftests/bpf/progs/sendmsg_unix_prog.c b/tools/testing/selftests/bpf/progs/sendmsg_unix_prog.c index d8869b03dda9..332d0eb1116f 100644 --- a/tools/testing/selftests/bpf/progs/sendmsg_unix_prog.c +++ b/tools/testing/selftests/bpf/progs/sendmsg_unix_prog.c @@ -36,4 +36,10 @@ int sendmsg_unix_prog(struct bpf_sock_addr *ctx) return 1; } +SEC("cgroup/sendmsg_unix") +int sendmsg_unix_deny_prog(struct bpf_sock_addr *ctx) +{ + return 0; +} + char _license[] SEC("license") = "GPL"; From bc467e953e4fbafd94d04c355f875bf1adf438e2 Mon Sep 17 00:00:00 2001 From: Jordan Rife Date: Fri, 10 May 2024 14:02:33 -0500 Subject: [PATCH 16/17] selftests/bpf: Expand getsockname and getpeername tests This expands coverage for getsockname and getpeername hooks to include getsockname4, getsockname6, getpeername4, and getpeername6. Signed-off-by: Jordan Rife Link: https://lore.kernel.org/r/20240510190246.3247730-17-jrife@google.com Signed-off-by: Alexei Starovoitov --- .../selftests/bpf/prog_tests/sock_addr.c | 304 +++++++++++++++++- .../selftests/bpf/progs/getpeername4_prog.c | 24 ++ .../selftests/bpf/progs/getpeername6_prog.c | 31 ++ .../selftests/bpf/progs/getsockname4_prog.c | 24 ++ .../selftests/bpf/progs/getsockname6_prog.c | 31 ++ 5 files changed, 412 insertions(+), 2 deletions(-) create mode 100644 tools/testing/selftests/bpf/progs/getpeername4_prog.c create mode 100644 tools/testing/selftests/bpf/progs/getpeername6_prog.c create mode 100644 tools/testing/selftests/bpf/progs/getsockname4_prog.c create mode 100644 tools/testing/selftests/bpf/progs/getsockname6_prog.c diff --git a/tools/testing/selftests/bpf/prog_tests/sock_addr.c b/tools/testing/selftests/bpf/prog_tests/sock_addr.c index 0477b4080b2e..a0a40bdcfe45 100644 --- a/tools/testing/selftests/bpf/prog_tests/sock_addr.c +++ b/tools/testing/selftests/bpf/prog_tests/sock_addr.c @@ -15,7 +15,11 @@ #include "recvmsg6_prog.skel.h" #include "sendmsg_unix_prog.skel.h" #include "recvmsg_unix_prog.skel.h" +#include "getsockname4_prog.skel.h" +#include "getsockname6_prog.skel.h" #include "getsockname_unix_prog.skel.h" +#include "getpeername4_prog.skel.h" +#include "getpeername6_prog.skel.h" #include "getpeername_unix_prog.skel.h" #include "network_helpers.h" @@ -466,7 +470,11 @@ BPF_SKEL_FUNCS(recvmsg4_prog, recvmsg4_prog); BPF_SKEL_FUNCS(recvmsg6_prog, recvmsg6_prog); BPF_SKEL_FUNCS(recvmsg_unix_prog, recvmsg_unix_prog); BPF_SKEL_FUNCS(getsockname_unix_prog, getsockname_unix_prog); +BPF_SKEL_FUNCS(getsockname4_prog, getsockname_v4_prog); +BPF_SKEL_FUNCS(getsockname6_prog, getsockname_v6_prog); BPF_SKEL_FUNCS(getpeername_unix_prog, getpeername_unix_prog); +BPF_SKEL_FUNCS(getpeername4_prog, getpeername_v4_prog); +BPF_SKEL_FUNCS(getpeername6_prog, getpeername_v6_prog); static struct sock_addr_test tests[] = { /* bind - system calls */ @@ -1688,7 +1696,71 @@ static struct sock_addr_test tests[] = { /* getsockname - system calls */ { SOCK_ADDR_TEST_GETSOCKNAME, - "getsockname_unix", + "getsockname4: getsockname (stream)", + getsockname_v4_prog_load, + getsockname_v4_prog_destroy, + BPF_CGROUP_INET4_GETSOCKNAME, + &user_ops, + AF_INET, + SOCK_STREAM, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + SERV4_IP, + SERV4_PORT, + NULL, + SUCCESS, + }, + { + SOCK_ADDR_TEST_GETSOCKNAME, + "getsockname4: getsockname (dgram)", + getsockname_v4_prog_load, + getsockname_v4_prog_destroy, + BPF_CGROUP_INET4_GETSOCKNAME, + &user_ops, + AF_INET, + SOCK_DGRAM, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + SERV4_IP, + SERV4_PORT, + NULL, + SUCCESS, + }, + { + SOCK_ADDR_TEST_GETSOCKNAME, + "getsockname6: getsockname (stream)", + getsockname_v6_prog_load, + getsockname_v6_prog_destroy, + BPF_CGROUP_INET6_GETSOCKNAME, + &user_ops, + AF_INET6, + SOCK_STREAM, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SERV6_IP, + SERV6_PORT, + NULL, + SUCCESS, + }, + { + SOCK_ADDR_TEST_GETSOCKNAME, + "getsockname6: getsockname (dgram)", + getsockname_v6_prog_load, + getsockname_v6_prog_destroy, + BPF_CGROUP_INET6_GETSOCKNAME, + &user_ops, + AF_INET6, + SOCK_DGRAM, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SERV6_IP, + SERV6_PORT, + NULL, + SUCCESS, + }, + { + SOCK_ADDR_TEST_GETSOCKNAME, + "getsockname_unix: getsockname", getsockname_unix_prog_load, getsockname_unix_prog_destroy, BPF_CGROUP_UNIX_GETSOCKNAME, @@ -1703,10 +1775,156 @@ static struct sock_addr_test tests[] = { SUCCESS, }, + /* getsockname - kernel calls */ + { + SOCK_ADDR_TEST_GETSOCKNAME, + "getsockname4: kernel_getsockname (stream)", + getsockname_v4_prog_load, + getsockname_v4_prog_destroy, + BPF_CGROUP_INET4_GETSOCKNAME, + &kern_ops_kernel_sendmsg, + AF_INET, + SOCK_STREAM, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + SERV4_IP, + SERV4_PORT, + NULL, + SUCCESS, + }, + { + SOCK_ADDR_TEST_GETSOCKNAME, + "getsockname4: kernel_getsockname (dgram)", + getsockname_v4_prog_load, + getsockname_v4_prog_destroy, + BPF_CGROUP_INET4_GETSOCKNAME, + &kern_ops_kernel_sendmsg, + AF_INET, + SOCK_DGRAM, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + SERV4_IP, + SERV4_PORT, + NULL, + SUCCESS, + }, + { + SOCK_ADDR_TEST_GETSOCKNAME, + "getsockname6: kernel_getsockname (stream)", + getsockname_v6_prog_load, + getsockname_v6_prog_destroy, + BPF_CGROUP_INET6_GETSOCKNAME, + &kern_ops_kernel_sendmsg, + AF_INET6, + SOCK_STREAM, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SERV6_IP, + SERV6_PORT, + NULL, + SUCCESS, + }, + { + SOCK_ADDR_TEST_GETSOCKNAME, + "getsockname6: kernel_getsockname (dgram)", + getsockname_v6_prog_load, + getsockname_v6_prog_destroy, + BPF_CGROUP_INET6_GETSOCKNAME, + &kern_ops_kernel_sendmsg, + AF_INET6, + SOCK_DGRAM, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SERV6_IP, + SERV6_PORT, + NULL, + SUCCESS, + }, + { + SOCK_ADDR_TEST_GETSOCKNAME, + "getsockname_unix: kernel_getsockname", + getsockname_unix_prog_load, + getsockname_unix_prog_destroy, + BPF_CGROUP_UNIX_GETSOCKNAME, + &kern_ops_kernel_sendmsg, + AF_UNIX, + SOCK_STREAM, + SERVUN_ADDRESS, + 0, + SERVUN_REWRITE_ADDRESS, + 0, + NULL, + SUCCESS, + }, + /* getpeername - system calls */ { SOCK_ADDR_TEST_GETPEERNAME, - "getpeername_unix", + "getpeername4: getpeername (stream)", + getpeername_v4_prog_load, + getpeername_v4_prog_destroy, + BPF_CGROUP_INET4_GETPEERNAME, + &user_ops, + AF_INET, + SOCK_STREAM, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + SERV4_IP, + SERV4_PORT, + NULL, + SUCCESS, + }, + { + SOCK_ADDR_TEST_GETPEERNAME, + "getpeername4: getpeername (dgram)", + getpeername_v4_prog_load, + getpeername_v4_prog_destroy, + BPF_CGROUP_INET4_GETPEERNAME, + &user_ops, + AF_INET, + SOCK_DGRAM, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + SERV4_IP, + SERV4_PORT, + NULL, + SUCCESS, + }, + { + SOCK_ADDR_TEST_GETPEERNAME, + "getpeername6: getpeername (stream)", + getpeername_v6_prog_load, + getpeername_v6_prog_destroy, + BPF_CGROUP_INET6_GETPEERNAME, + &user_ops, + AF_INET6, + SOCK_STREAM, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SERV6_IP, + SERV6_PORT, + NULL, + SUCCESS, + }, + { + SOCK_ADDR_TEST_GETPEERNAME, + "getpeername6: getpeername (dgram)", + getpeername_v6_prog_load, + getpeername_v6_prog_destroy, + BPF_CGROUP_INET6_GETPEERNAME, + &user_ops, + AF_INET6, + SOCK_DGRAM, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SERV6_IP, + SERV6_PORT, + NULL, + SUCCESS, + }, + { + SOCK_ADDR_TEST_GETPEERNAME, + "getpeername_unix: getpeername", getpeername_unix_prog_load, getpeername_unix_prog_destroy, BPF_CGROUP_UNIX_GETPEERNAME, @@ -1720,6 +1938,88 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + + /* getpeername - kernel calls */ + { + SOCK_ADDR_TEST_GETPEERNAME, + "getpeername4: kernel_getpeername (stream)", + getpeername_v4_prog_load, + getpeername_v4_prog_destroy, + BPF_CGROUP_INET4_GETPEERNAME, + &kern_ops_kernel_sendmsg, + AF_INET, + SOCK_STREAM, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + SERV4_IP, + SERV4_PORT, + NULL, + SUCCESS, + }, + { + SOCK_ADDR_TEST_GETPEERNAME, + "getpeername4: kernel_getpeername (dgram)", + getpeername_v4_prog_load, + getpeername_v4_prog_destroy, + BPF_CGROUP_INET4_GETPEERNAME, + &kern_ops_kernel_sendmsg, + AF_INET, + SOCK_DGRAM, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + SERV4_IP, + SERV4_PORT, + NULL, + SUCCESS, + }, + { + SOCK_ADDR_TEST_GETPEERNAME, + "getpeername6: kernel_getpeername (stream)", + getpeername_v6_prog_load, + getpeername_v6_prog_destroy, + BPF_CGROUP_INET6_GETPEERNAME, + &kern_ops_kernel_sendmsg, + AF_INET6, + SOCK_STREAM, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SERV6_IP, + SERV6_PORT, + NULL, + SUCCESS, + }, + { + SOCK_ADDR_TEST_GETPEERNAME, + "getpeername6: kernel_getpeername (dgram)", + getpeername_v6_prog_load, + getpeername_v6_prog_destroy, + BPF_CGROUP_INET6_GETPEERNAME, + &kern_ops_kernel_sendmsg, + AF_INET6, + SOCK_DGRAM, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SERV6_IP, + SERV6_PORT, + NULL, + SUCCESS, + }, + { + SOCK_ADDR_TEST_GETPEERNAME, + "getpeername_unix: kernel_getpeername", + getpeername_unix_prog_load, + getpeername_unix_prog_destroy, + BPF_CGROUP_UNIX_GETPEERNAME, + &kern_ops_kernel_sendmsg, + AF_UNIX, + SOCK_STREAM, + SERVUN_ADDRESS, + 0, + SERVUN_REWRITE_ADDRESS, + 0, + NULL, + SUCCESS, + }, }; typedef int (*info_fn)(int, struct sockaddr *, socklen_t *); diff --git a/tools/testing/selftests/bpf/progs/getpeername4_prog.c b/tools/testing/selftests/bpf/progs/getpeername4_prog.c new file mode 100644 index 000000000000..4c97208cd25d --- /dev/null +++ b/tools/testing/selftests/bpf/progs/getpeername4_prog.c @@ -0,0 +1,24 @@ +// SPDX-License-Identifier: GPL-2.0 +/* Copyright (c) 2024 Google LLC */ + +#include "vmlinux.h" + +#include +#include +#include +#include +#include "bpf_kfuncs.h" + +#define REWRITE_ADDRESS_IP4 0xc0a801fe // 192.168.1.254 +#define REWRITE_ADDRESS_PORT4 4040 + +SEC("cgroup/getpeername4") +int getpeername_v4_prog(struct bpf_sock_addr *ctx) +{ + ctx->user_ip4 = bpf_htonl(REWRITE_ADDRESS_IP4); + ctx->user_port = bpf_htons(REWRITE_ADDRESS_PORT4); + + return 1; +} + +char _license[] SEC("license") = "GPL"; diff --git a/tools/testing/selftests/bpf/progs/getpeername6_prog.c b/tools/testing/selftests/bpf/progs/getpeername6_prog.c new file mode 100644 index 000000000000..070e4d7f636c --- /dev/null +++ b/tools/testing/selftests/bpf/progs/getpeername6_prog.c @@ -0,0 +1,31 @@ +// SPDX-License-Identifier: GPL-2.0 +/* Copyright (c) 2024 Google LLC */ + +#include "vmlinux.h" + +#include +#include +#include +#include +#include "bpf_kfuncs.h" + +#define REWRITE_ADDRESS_IP6_0 0xfaceb00c +#define REWRITE_ADDRESS_IP6_1 0x12345678 +#define REWRITE_ADDRESS_IP6_2 0x00000000 +#define REWRITE_ADDRESS_IP6_3 0x0000abcd + +#define REWRITE_ADDRESS_PORT6 6060 + +SEC("cgroup/getpeername6") +int getpeername_v6_prog(struct bpf_sock_addr *ctx) +{ + ctx->user_ip6[0] = bpf_htonl(REWRITE_ADDRESS_IP6_0); + ctx->user_ip6[1] = bpf_htonl(REWRITE_ADDRESS_IP6_1); + ctx->user_ip6[2] = bpf_htonl(REWRITE_ADDRESS_IP6_2); + ctx->user_ip6[3] = bpf_htonl(REWRITE_ADDRESS_IP6_3); + ctx->user_port = bpf_htons(REWRITE_ADDRESS_PORT6); + + return 1; +} + +char _license[] SEC("license") = "GPL"; diff --git a/tools/testing/selftests/bpf/progs/getsockname4_prog.c b/tools/testing/selftests/bpf/progs/getsockname4_prog.c new file mode 100644 index 000000000000..e298487c6347 --- /dev/null +++ b/tools/testing/selftests/bpf/progs/getsockname4_prog.c @@ -0,0 +1,24 @@ +// SPDX-License-Identifier: GPL-2.0 +/* Copyright (c) 2024 Google LLC */ + +#include "vmlinux.h" + +#include +#include +#include +#include +#include "bpf_kfuncs.h" + +#define REWRITE_ADDRESS_IP4 0xc0a801fe // 192.168.1.254 +#define REWRITE_ADDRESS_PORT4 4040 + +SEC("cgroup/getsockname4") +int getsockname_v4_prog(struct bpf_sock_addr *ctx) +{ + ctx->user_ip4 = bpf_htonl(REWRITE_ADDRESS_IP4); + ctx->user_port = bpf_htons(REWRITE_ADDRESS_PORT4); + + return 1; +} + +char _license[] SEC("license") = "GPL"; diff --git a/tools/testing/selftests/bpf/progs/getsockname6_prog.c b/tools/testing/selftests/bpf/progs/getsockname6_prog.c new file mode 100644 index 000000000000..811d10cd5525 --- /dev/null +++ b/tools/testing/selftests/bpf/progs/getsockname6_prog.c @@ -0,0 +1,31 @@ +// SPDX-License-Identifier: GPL-2.0 +/* Copyright (c) 2024 Google LLC */ + +#include "vmlinux.h" + +#include +#include +#include +#include +#include "bpf_kfuncs.h" + +#define REWRITE_ADDRESS_IP6_0 0xfaceb00c +#define REWRITE_ADDRESS_IP6_1 0x12345678 +#define REWRITE_ADDRESS_IP6_2 0x00000000 +#define REWRITE_ADDRESS_IP6_3 0x0000abcd + +#define REWRITE_ADDRESS_PORT6 6060 + +SEC("cgroup/getsockname6") +int getsockname_v6_prog(struct bpf_sock_addr *ctx) +{ + ctx->user_ip6[0] = bpf_htonl(REWRITE_ADDRESS_IP6_0); + ctx->user_ip6[1] = bpf_htonl(REWRITE_ADDRESS_IP6_1); + ctx->user_ip6[2] = bpf_htonl(REWRITE_ADDRESS_IP6_2); + ctx->user_ip6[3] = bpf_htonl(REWRITE_ADDRESS_IP6_3); + ctx->user_port = bpf_htons(REWRITE_ADDRESS_PORT6); + + return 1; +} + +char _license[] SEC("license") = "GPL"; From a3d3eb957ddc733d04c0da67024b1c30d8826cc2 Mon Sep 17 00:00:00 2001 From: Jordan Rife Date: Fri, 10 May 2024 14:02:34 -0500 Subject: [PATCH 17/17] selftests/bpf: Expand ATTACH_REJECT tests This expands coverage for ATTACH_REJECT tests to include connect_unix, sendmsg_unix, recvmsg*, getsockname*, and getpeername*. Signed-off-by: Jordan Rife Link: https://lore.kernel.org/r/20240510190246.3247730-18-jrife@google.com Signed-off-by: Alexei Starovoitov --- .../selftests/bpf/prog_tests/sock_addr.c | 187 ++++++++++++++++++ 1 file changed, 187 insertions(+) diff --git a/tools/testing/selftests/bpf/prog_tests/sock_addr.c b/tools/testing/selftests/bpf/prog_tests/sock_addr.c index a0a40bdcfe45..b880c564a204 100644 --- a/tools/testing/selftests/bpf/prog_tests/sock_addr.c +++ b/tools/testing/selftests/bpf/prog_tests/sock_addr.c @@ -454,6 +454,7 @@ BPF_SKEL_FUNCS(connect6_prog, connect_v6_prog); BPF_SKEL_FUNCS_RAW(connect6_prog, connect_v6_prog); BPF_SKEL_FUNCS(connect6_prog, connect_v6_deny_prog); BPF_SKEL_FUNCS(connect_unix_prog, connect_unix_prog); +BPF_SKEL_FUNCS_RAW(connect_unix_prog, connect_unix_prog); BPF_SKEL_FUNCS(connect_unix_prog, connect_unix_deny_prog); BPF_SKEL_FUNCS(sendmsg4_prog, sendmsg_v4_prog); BPF_SKEL_FUNCS_RAW(sendmsg4_prog, sendmsg_v4_prog); @@ -465,16 +466,26 @@ BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_preserve_dst_prog); BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_v4mapped_prog); BPF_SKEL_FUNCS(sendmsg6_prog, sendmsg_v6_wildcard_prog); BPF_SKEL_FUNCS(sendmsg_unix_prog, sendmsg_unix_prog); +BPF_SKEL_FUNCS_RAW(sendmsg_unix_prog, sendmsg_unix_prog); BPF_SKEL_FUNCS(sendmsg_unix_prog, sendmsg_unix_deny_prog); BPF_SKEL_FUNCS(recvmsg4_prog, recvmsg4_prog); +BPF_SKEL_FUNCS_RAW(recvmsg4_prog, recvmsg4_prog); BPF_SKEL_FUNCS(recvmsg6_prog, recvmsg6_prog); +BPF_SKEL_FUNCS_RAW(recvmsg6_prog, recvmsg6_prog); BPF_SKEL_FUNCS(recvmsg_unix_prog, recvmsg_unix_prog); +BPF_SKEL_FUNCS_RAW(recvmsg_unix_prog, recvmsg_unix_prog); BPF_SKEL_FUNCS(getsockname_unix_prog, getsockname_unix_prog); +BPF_SKEL_FUNCS_RAW(getsockname_unix_prog, getsockname_unix_prog); BPF_SKEL_FUNCS(getsockname4_prog, getsockname_v4_prog); +BPF_SKEL_FUNCS_RAW(getsockname4_prog, getsockname_v4_prog); BPF_SKEL_FUNCS(getsockname6_prog, getsockname_v6_prog); +BPF_SKEL_FUNCS_RAW(getsockname6_prog, getsockname_v6_prog); BPF_SKEL_FUNCS(getpeername_unix_prog, getpeername_unix_prog); +BPF_SKEL_FUNCS_RAW(getpeername_unix_prog, getpeername_unix_prog); BPF_SKEL_FUNCS(getpeername4_prog, getpeername_v4_prog); +BPF_SKEL_FUNCS_RAW(getpeername4_prog, getpeername_v4_prog); BPF_SKEL_FUNCS(getpeername6_prog, getpeername_v6_prog); +BPF_SKEL_FUNCS_RAW(getpeername6_prog, getpeername_v6_prog); static struct sock_addr_test tests[] = { /* bind - system calls */ @@ -1026,6 +1037,22 @@ static struct sock_addr_test tests[] = { NULL, SYSCALL_EPERM, }, + { + SOCK_ADDR_TEST_CONNECT, + "connect_unix: attach prog with wrong attach type", + connect_unix_prog_load_raw, + connect_unix_prog_destroy_raw, + BPF_CGROUP_INET4_CONNECT, + &user_ops, + AF_UNIX, + SOCK_STREAM, + SERVUN_ADDRESS, + 0, + SERVUN_REWRITE_ADDRESS, + 0, + NULL, + ATTACH_REJECT, + }, /* connect - kernel calls */ { @@ -1398,6 +1425,22 @@ static struct sock_addr_test tests[] = { NULL, SYSCALL_EPERM, }, + { + SOCK_ADDR_TEST_SENDMSG, + "sendmsg_unix: attach prog with wrong attach type", + sendmsg_unix_prog_load_raw, + sendmsg_unix_prog_destroy_raw, + BPF_CGROUP_UDP4_SENDMSG, + &user_ops, + AF_UNIX, + SOCK_DGRAM, + SERVUN_ADDRESS, + 0, + SERVUN_REWRITE_ADDRESS, + 0, + NULL, + ATTACH_REJECT, + }, /* sendmsg - kernel calls (sock_sendmsg) */ { @@ -1644,6 +1687,22 @@ static struct sock_addr_test tests[] = { SERV4_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_RECVMSG, + "recvmsg4: attach prog with wrong attach type", + recvmsg4_prog_load_raw, + recvmsg4_prog_destroy_raw, + BPF_CGROUP_UDP6_RECVMSG, + &user_ops, + AF_INET, + SOCK_DGRAM, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + SERV4_IP, + ATTACH_REJECT, + }, { SOCK_ADDR_TEST_RECVMSG, "recvmsg6: recvfrom (dgram)", @@ -1660,6 +1719,22 @@ static struct sock_addr_test tests[] = { SERV6_IP, SUCCESS, }, + { + SOCK_ADDR_TEST_RECVMSG, + "recvmsg6: attach prog with wrong attach type", + recvmsg6_prog_load_raw, + recvmsg6_prog_destroy_raw, + BPF_CGROUP_UDP4_RECVMSG, + &user_ops, + AF_INET6, + SOCK_DGRAM, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SERV6_IP, + ATTACH_REJECT, + }, { SOCK_ADDR_TEST_RECVMSG, "recvmsg_unix: recvfrom (dgram)", @@ -1692,6 +1767,22 @@ static struct sock_addr_test tests[] = { SERVUN_ADDRESS, SUCCESS, }, + { + SOCK_ADDR_TEST_RECVMSG, + "recvmsg_unix: attach prog with wrong attach type", + recvmsg_unix_prog_load_raw, + recvmsg_unix_prog_destroy_raw, + BPF_CGROUP_UDP4_RECVMSG, + &user_ops, + AF_INET6, + SOCK_STREAM, + SERVUN_REWRITE_ADDRESS, + 0, + SERVUN_REWRITE_ADDRESS, + 0, + SERVUN_ADDRESS, + ATTACH_REJECT, + }, /* getsockname - system calls */ { @@ -1726,6 +1817,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_GETSOCKNAME, + "getsockname4: attach prog with wrong attach type", + getsockname_v4_prog_load_raw, + getsockname_v4_prog_destroy_raw, + BPF_CGROUP_INET6_GETSOCKNAME, + &user_ops, + AF_INET, + SOCK_DGRAM, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + SERV4_IP, + SERV4_PORT, + NULL, + ATTACH_REJECT, + }, { SOCK_ADDR_TEST_GETSOCKNAME, "getsockname6: getsockname (stream)", @@ -1758,6 +1865,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_GETSOCKNAME, + "getsockname6: attach prog with wrong attach type", + getsockname_v6_prog_load_raw, + getsockname_v6_prog_destroy_raw, + BPF_CGROUP_INET4_GETSOCKNAME, + &user_ops, + AF_INET6, + SOCK_DGRAM, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SERV6_IP, + SERV6_PORT, + NULL, + ATTACH_REJECT, + }, { SOCK_ADDR_TEST_GETSOCKNAME, "getsockname_unix: getsockname", @@ -1774,6 +1897,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_GETSOCKNAME, + "getsockname_unix: attach prog with wrong attach type", + getsockname_unix_prog_load_raw, + getsockname_unix_prog_destroy_raw, + BPF_CGROUP_INET4_GETSOCKNAME, + &user_ops, + AF_UNIX, + SOCK_STREAM, + SERVUN_ADDRESS, + 0, + SERVUN_REWRITE_ADDRESS, + 0, + NULL, + ATTACH_REJECT, + }, /* getsockname - kernel calls */ { @@ -1890,6 +2029,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_GETPEERNAME, + "getpeername4: attach prog with wrong attach type", + getpeername_v4_prog_load_raw, + getpeername_v4_prog_destroy_raw, + BPF_CGROUP_INET6_GETSOCKNAME, + &user_ops, + AF_UNIX, + SOCK_DGRAM, + SERV4_REWRITE_IP, + SERV4_REWRITE_PORT, + SERV4_IP, + SERV4_PORT, + NULL, + ATTACH_REJECT, + }, { SOCK_ADDR_TEST_GETPEERNAME, "getpeername6: getpeername (stream)", @@ -1922,6 +2077,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_GETPEERNAME, + "getpeername6: attach prog with wrong attach type", + getpeername_v6_prog_load_raw, + getpeername_v6_prog_destroy_raw, + BPF_CGROUP_INET4_GETSOCKNAME, + &user_ops, + AF_INET6, + SOCK_DGRAM, + SERV6_REWRITE_IP, + SERV6_REWRITE_PORT, + SERV6_IP, + SERV6_PORT, + NULL, + ATTACH_REJECT, + }, { SOCK_ADDR_TEST_GETPEERNAME, "getpeername_unix: getpeername", @@ -1938,6 +2109,22 @@ static struct sock_addr_test tests[] = { NULL, SUCCESS, }, + { + SOCK_ADDR_TEST_GETPEERNAME, + "getpeername_unix: attach prog with wrong attach type", + getpeername_unix_prog_load_raw, + getpeername_unix_prog_destroy_raw, + BPF_CGROUP_INET4_GETSOCKNAME, + &user_ops, + AF_UNIX, + SOCK_STREAM, + SERVUN_ADDRESS, + 0, + SERVUN_REWRITE_ADDRESS, + 0, + NULL, + ATTACH_REJECT, + }, /* getpeername - kernel calls */ {