forked from torvalds/linux
-
Notifications
You must be signed in to change notification settings - Fork 1
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
samples, bpf: Add automated test for cgroup filter attachments
This patch adds the sample program test_cgrp2_attach2. This program is similar to test_cgrp2_attach, but it performs automated testing of the cgroupv2 BPF attached filters. It runs the following checks: * Simple filter attachment * Application of filters to child cgroups * Overriding filters on child cgroups * Checking that this still works when the parent filter is removed The filters that are used here are simply allow all / deny all filters, so it isn't checking the actual functionality of the filters, but rather the behaviour around detachment / attachment. If net_cls is enabled, this test will fail. Signed-off-by: Sargun Dhillon <[email protected]> Acked-by: Alexei Starovoitov <[email protected]> Signed-off-by: David S. Miller <[email protected]>
- Loading branch information
Showing
2 changed files
with
134 additions
and
0 deletions.
There are no files selected for viewing
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
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,132 @@ | ||
/* eBPF example program: | ||
* | ||
* - Creates arraymap in kernel with 4 bytes keys and 8 byte values | ||
* | ||
* - Loads eBPF program | ||
* | ||
* The eBPF program accesses the map passed in to store two pieces of | ||
* information. The number of invocations of the program, which maps | ||
* to the number of packets received, is stored to key 0. Key 1 is | ||
* incremented on each iteration by the number of bytes stored in | ||
* the skb. | ||
* | ||
* - Attaches the new program to a cgroup using BPF_PROG_ATTACH | ||
* | ||
* - Every second, reads map[0] and map[1] to see how many bytes and | ||
* packets were seen on any socket of tasks in the given cgroup. | ||
*/ | ||
|
||
#define _GNU_SOURCE | ||
|
||
#include <stdio.h> | ||
#include <stdlib.h> | ||
#include <assert.h> | ||
#include <unistd.h> | ||
|
||
#include <linux/bpf.h> | ||
|
||
#include "libbpf.h" | ||
#include "cgroup_helpers.h" | ||
|
||
#define FOO "/foo" | ||
#define BAR "/foo/bar/" | ||
#define PING_CMD "ping -c1 -w1 127.0.0.1" | ||
|
||
static int prog_load(int verdict) | ||
{ | ||
int ret; | ||
struct bpf_insn prog[] = { | ||
BPF_MOV64_IMM(BPF_REG_0, verdict), /* r0 = verdict */ | ||
BPF_EXIT_INSN(), | ||
}; | ||
|
||
ret = bpf_prog_load(BPF_PROG_TYPE_CGROUP_SKB, | ||
prog, sizeof(prog), "GPL", 0); | ||
|
||
if (ret < 0) { | ||
log_err("Loading program"); | ||
printf("Output from verifier:\n%s\n-------\n", bpf_log_buf); | ||
return 0; | ||
} | ||
return ret; | ||
} | ||
|
||
|
||
int main(int argc, char **argv) | ||
{ | ||
int drop_prog, allow_prog, foo = 0, bar = 0, rc = 0; | ||
|
||
allow_prog = prog_load(1); | ||
if (!allow_prog) | ||
goto err; | ||
|
||
drop_prog = prog_load(0); | ||
if (!drop_prog) | ||
goto err; | ||
|
||
if (setup_cgroup_environment()) | ||
goto err; | ||
|
||
/* Create cgroup /foo, get fd, and join it */ | ||
foo = create_and_get_cgroup(FOO); | ||
if (!foo) | ||
goto err; | ||
|
||
if (join_cgroup(FOO)) | ||
goto err; | ||
|
||
if (bpf_prog_attach(drop_prog, foo, BPF_CGROUP_INET_EGRESS)) { | ||
log_err("Attaching prog to /foo"); | ||
goto err; | ||
} | ||
|
||
assert(system(PING_CMD) != 0); | ||
|
||
/* Create cgroup /foo/bar, get fd, and join it */ | ||
bar = create_and_get_cgroup(BAR); | ||
if (!bar) | ||
goto err; | ||
|
||
if (join_cgroup(BAR)) | ||
goto err; | ||
|
||
assert(system(PING_CMD) != 0); | ||
|
||
if (bpf_prog_attach(allow_prog, bar, BPF_CGROUP_INET_EGRESS)) { | ||
log_err("Attaching prog to /foo/bar"); | ||
goto err; | ||
} | ||
|
||
assert(system(PING_CMD) == 0); | ||
|
||
|
||
if (bpf_prog_detach(bar, BPF_CGROUP_INET_EGRESS)) { | ||
log_err("Detaching program from /foo/bar"); | ||
goto err; | ||
} | ||
|
||
assert(system(PING_CMD) != 0); | ||
|
||
if (bpf_prog_attach(allow_prog, bar, BPF_CGROUP_INET_EGRESS)) { | ||
log_err("Attaching prog to /foo/bar"); | ||
goto err; | ||
} | ||
|
||
if (bpf_prog_detach(foo, BPF_CGROUP_INET_EGRESS)) { | ||
log_err("Detaching program from /foo"); | ||
goto err; | ||
} | ||
|
||
assert(system(PING_CMD) == 0); | ||
|
||
goto out; | ||
|
||
err: | ||
rc = 1; | ||
|
||
out: | ||
close(foo); | ||
close(bar); | ||
cleanup_cgroup_environment(); | ||
return rc; | ||
} |