Skip to content

Commit 31e5175

Browse files
author
yimingx
committed
feat: tailcall test
1 parent 61ac1f2 commit 31e5175

File tree

3 files changed

+106
-0
lines changed

3 files changed

+106
-0
lines changed

core/bpftests/stackmem.c

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
#include <linux/bpf.h>
2+
#include <bpf/bpf_helpers.h>
3+
4+
char LICENSE[] SEC("license") = "GPL";
5+
6+
SEC("tracepoint/syscalls/sys_enter_mount")
7+
int prog(void *ctx)
8+
{
9+
10+
volatile int a;
11+
bpf_printk("r10 - 8: %p: %d\n", &a, a);
12+
long* r10 = (long*)((int*)(&a) + 1);
13+
bpf_printk("r10: %p: %d\n", r10, *r10); // Invalid
14+
15+
bpf_printk("entry_prog: tail call failed\n");
16+
return XDP_PASS;
17+
}

core/bpftests/tailcall.c

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
// tailcall_kern.c
2+
#include "vmlinux.h"
3+
#include <bpf/bpf_helpers.h>
4+
5+
char LICENSE[] SEC("license") = "GPL";
6+
7+
// Program array map
8+
struct {
9+
__uint(type, BPF_MAP_TYPE_PROG_ARRAY);
10+
__uint(max_entries, 4);
11+
__type(key, __u32);
12+
__type(value, __u32);
13+
} jmp_table SEC(".maps");
14+
15+
// Entry program
16+
SEC("tracepoint/syscalls/sys_enter_mount")
17+
int entry_prog(void *ctx)
18+
{
19+
__u32 index = 1;
20+
21+
// int a[5] = { 1, 2, 3, 4, 5 };
22+
volatile int a = 100;
23+
bpf_printk("p1 %p\n", &a);
24+
25+
// Tail call to index 1
26+
bpf_tail_call(ctx, &jmp_table, index);
27+
28+
bpf_printk("entry_prog: tail call failed\n");
29+
return XDP_PASS;
30+
}
31+
32+
// Program that is tail-called
33+
SEC("tracepoint/syscalls/sys_enter_mount")
34+
int next_prog(void *ctx)
35+
{
36+
volatile int a;
37+
bpf_printk("p2 %p\n", &a);
38+
bpf_printk("p2 %d\n", a);
39+
return XDP_PASS;
40+
}

core/bpftests/tailcall_us.c

Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
// tailcall_user.c
2+
#include <stdio.h>
3+
#include <bpf/libbpf.h>
4+
#include <bpf/bpf.h>
5+
#include <unistd.h>
6+
int main()
7+
{
8+
struct bpf_object *obj;
9+
struct bpf_program *p_entry, *p_next;
10+
int prog_fd_entry, prog_fd_next;
11+
int map_fd;
12+
13+
obj = bpf_object__open_file("output/tailcall.o", NULL);
14+
if (!obj) {
15+
printf("open failed\n");
16+
return 1;
17+
}
18+
19+
if (bpf_object__load(obj)) {
20+
printf("load failed\n");
21+
return 1;
22+
}
23+
24+
p_entry = bpf_object__find_program_by_name(obj, "entry_prog");
25+
p_next = bpf_object__find_program_by_name(obj, "next_prog");
26+
27+
prog_fd_entry = bpf_program__fd(p_entry);
28+
prog_fd_next = bpf_program__fd(p_next);
29+
30+
map_fd = bpf_object__find_map_fd_by_name(obj, "jmp_table");
31+
32+
__u32 index = 1;
33+
if (bpf_map_update_elem(map_fd, &index, &prog_fd_next, 0)) {
34+
printf("update_elem failed\n");
35+
return 1;
36+
}
37+
38+
struct bpf_link *link1 = NULL, *link2 = NULL, *link3 = NULL;
39+
40+
link1 = bpf_program__attach_tracepoint(p_entry, "syscalls",
41+
"sys_enter_mount");
42+
if (libbpf_get_error(link1)) {
43+
fprintf(stderr, "Failed to attach\n");
44+
return 1;
45+
}
46+
sleep(30);
47+
bpf_link__destroy(link1);
48+
return 0;
49+
}

0 commit comments

Comments
 (0)