-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
bpf: selftests: introduce bpf_xdp_{load,store}_bytes selftest
Introduce kernel selftest for new bpf_xdp_{load,store}_bytes helpers. and bpf_xdp_pointer/bpf_xdp_copy_buf utility routines. Acked-by: Toke Hoiland-Jorgensen <toke@redhat.com> Acked-by: John Fastabend <john.fastabend@gmail.com> Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org> Link: https://lore.kernel.org/r/2c99ae663a5dcfbd9240b1d0489ad55dea4f4601.1642758637.git.lorenzo@kernel.org Signed-off-by: Alexei Starovoitov <ast@kernel.org>
- Loading branch information
Lorenzo Bianconi
authored and
Alexei Starovoitov
committed
Jan 21, 2022
1 parent
3f36422
commit 6db28e2
Showing
2 changed files
with
146 additions
and
0 deletions.
There are no files selected for viewing
104 changes: 104 additions & 0 deletions
104
tools/testing/selftests/bpf/prog_tests/xdp_adjust_frags.c
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,104 @@ | ||
// SPDX-License-Identifier: GPL-2.0 | ||
#include <test_progs.h> | ||
#include <network_helpers.h> | ||
|
||
void test_xdp_update_frags(void) | ||
{ | ||
const char *file = "./test_xdp_update_frags.o"; | ||
__u32 duration, retval, size; | ||
struct bpf_program *prog; | ||
struct bpf_object *obj; | ||
int err, prog_fd; | ||
__u32 *offset; | ||
__u8 *buf; | ||
|
||
obj = bpf_object__open(file); | ||
if (libbpf_get_error(obj)) | ||
return; | ||
|
||
prog = bpf_object__next_program(obj, NULL); | ||
if (bpf_object__load(obj)) | ||
return; | ||
|
||
prog_fd = bpf_program__fd(prog); | ||
|
||
buf = malloc(128); | ||
if (!ASSERT_OK_PTR(buf, "alloc buf 128b")) | ||
goto out; | ||
|
||
memset(buf, 0, 128); | ||
offset = (__u32 *)buf; | ||
*offset = 16; | ||
buf[*offset] = 0xaa; /* marker at offset 16 (head) */ | ||
buf[*offset + 15] = 0xaa; /* marker at offset 31 (head) */ | ||
|
||
err = bpf_prog_test_run(prog_fd, 1, buf, 128, | ||
buf, &size, &retval, &duration); | ||
|
||
/* test_xdp_update_frags: buf[16,31]: 0xaa -> 0xbb */ | ||
ASSERT_OK(err, "xdp_update_frag"); | ||
ASSERT_EQ(retval, XDP_PASS, "xdp_update_frag retval"); | ||
ASSERT_EQ(buf[16], 0xbb, "xdp_update_frag buf[16]"); | ||
ASSERT_EQ(buf[31], 0xbb, "xdp_update_frag buf[31]"); | ||
|
||
free(buf); | ||
|
||
buf = malloc(9000); | ||
if (!ASSERT_OK_PTR(buf, "alloc buf 9Kb")) | ||
goto out; | ||
|
||
memset(buf, 0, 9000); | ||
offset = (__u32 *)buf; | ||
*offset = 5000; | ||
buf[*offset] = 0xaa; /* marker at offset 5000 (frag0) */ | ||
buf[*offset + 15] = 0xaa; /* marker at offset 5015 (frag0) */ | ||
|
||
err = bpf_prog_test_run(prog_fd, 1, buf, 9000, | ||
buf, &size, &retval, &duration); | ||
|
||
/* test_xdp_update_frags: buf[5000,5015]: 0xaa -> 0xbb */ | ||
ASSERT_OK(err, "xdp_update_frag"); | ||
ASSERT_EQ(retval, XDP_PASS, "xdp_update_frag retval"); | ||
ASSERT_EQ(buf[5000], 0xbb, "xdp_update_frag buf[5000]"); | ||
ASSERT_EQ(buf[5015], 0xbb, "xdp_update_frag buf[5015]"); | ||
|
||
memset(buf, 0, 9000); | ||
offset = (__u32 *)buf; | ||
*offset = 3510; | ||
buf[*offset] = 0xaa; /* marker at offset 3510 (head) */ | ||
buf[*offset + 15] = 0xaa; /* marker at offset 3525 (frag0) */ | ||
|
||
err = bpf_prog_test_run(prog_fd, 1, buf, 9000, | ||
buf, &size, &retval, &duration); | ||
|
||
/* test_xdp_update_frags: buf[3510,3525]: 0xaa -> 0xbb */ | ||
ASSERT_OK(err, "xdp_update_frag"); | ||
ASSERT_EQ(retval, XDP_PASS, "xdp_update_frag retval"); | ||
ASSERT_EQ(buf[3510], 0xbb, "xdp_update_frag buf[3510]"); | ||
ASSERT_EQ(buf[3525], 0xbb, "xdp_update_frag buf[3525]"); | ||
|
||
memset(buf, 0, 9000); | ||
offset = (__u32 *)buf; | ||
*offset = 7606; | ||
buf[*offset] = 0xaa; /* marker at offset 7606 (frag0) */ | ||
buf[*offset + 15] = 0xaa; /* marker at offset 7621 (frag1) */ | ||
|
||
err = bpf_prog_test_run(prog_fd, 1, buf, 9000, | ||
buf, &size, &retval, &duration); | ||
|
||
/* test_xdp_update_frags: buf[7606,7621]: 0xaa -> 0xbb */ | ||
ASSERT_OK(err, "xdp_update_frag"); | ||
ASSERT_EQ(retval, XDP_PASS, "xdp_update_frag retval"); | ||
ASSERT_EQ(buf[7606], 0xbb, "xdp_update_frag buf[7606]"); | ||
ASSERT_EQ(buf[7621], 0xbb, "xdp_update_frag buf[7621]"); | ||
|
||
free(buf); | ||
out: | ||
bpf_object__close(obj); | ||
} | ||
|
||
void test_xdp_adjust_frags(void) | ||
{ | ||
if (test__start_subtest("xdp_adjust_frags")) | ||
test_xdp_update_frags(); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,42 @@ | ||
// SPDX-License-Identifier: GPL-2.0 | ||
/* | ||
* This program is free software; you can redistribute it and/or | ||
* modify it under the terms of version 2 of the GNU General Public | ||
* License as published by the Free Software Foundation. | ||
*/ | ||
#include <linux/bpf.h> | ||
#include <linux/if_ether.h> | ||
#include <bpf/bpf_helpers.h> | ||
|
||
int _version SEC("version") = 1; | ||
|
||
SEC("xdp.frags") | ||
int xdp_adjust_frags(struct xdp_md *xdp) | ||
{ | ||
__u8 *data_end = (void *)(long)xdp->data_end; | ||
__u8 *data = (void *)(long)xdp->data; | ||
__u8 val[16] = {}; | ||
__u32 offset; | ||
int err; | ||
|
||
if (data + sizeof(__u32) > data_end) | ||
return XDP_DROP; | ||
|
||
offset = *(__u32 *)data; | ||
err = bpf_xdp_load_bytes(xdp, offset, val, sizeof(val)); | ||
if (err < 0) | ||
return XDP_DROP; | ||
|
||
if (val[0] != 0xaa || val[15] != 0xaa) /* marker */ | ||
return XDP_DROP; | ||
|
||
val[0] = 0xbb; /* update the marker */ | ||
val[15] = 0xbb; | ||
err = bpf_xdp_store_bytes(xdp, offset, val, sizeof(val)); | ||
if (err < 0) | ||
return XDP_DROP; | ||
|
||
return XDP_PASS; | ||
} | ||
|
||
char _license[] SEC("license") = "GPL"; |