@@ -257,18 +257,48 @@ EXAMPLES
257257 return 0;
258258 }
259259
260- This is example BPF application with two BPF programs and a mix of BPF maps
261- and global variables. Source code is split across two source code files.
260+ **$ cat example3.bpf.c **
261+
262+ ::
263+
264+ #include <linux/ptrace.h>
265+ #include <linux/bpf.h>
266+ #include <bpf/bpf_helpers.h>
267+ /* This header file is provided by the bpf_testmod module. */
268+ #include "bpf_testmod.h"
269+
270+ int test_2_result = 0;
271+
272+ /* bpf_Testmod.ko calls this function, passing a "4"
273+ * and testmod_map->data.
274+ */
275+ SEC("struct_ops/test_2")
276+ void BPF_PROG(test_2, int a, int b)
277+ {
278+ test_2_result = a + b;
279+ }
280+
281+ SEC(".struct_ops")
282+ struct bpf_testmod_ops testmod_map = {
283+ .test_2 = (void *)test_2,
284+ .data = 0x1,
285+ };
286+
287+ This is example BPF application with three BPF programs and a mix of BPF
288+ maps and global variables. Source code is split across three source code
289+ files.
262290
263291**$ clang --target=bpf -g example1.bpf.c -o example1.bpf.o **
264292
265293**$ clang --target=bpf -g example2.bpf.c -o example2.bpf.o **
266294
267- **$ bpftool gen object example.bpf.o example1.bpf.o example2.bpf.o **
295+ **$ clang --target=bpf -g example3.bpf.c -o example3.bpf.o **
296+
297+ **$ bpftool gen object example.bpf.o example1.bpf.o example2.bpf.o example3.bpf.o **
268298
269- This set of commands compiles *example1.bpf.c * and *example2.bpf.c *
270- individually and then statically links respective object files into the final
271- BPF ELF object file *example.bpf.o *.
299+ This set of commands compiles *example1.bpf.c *, *example2.bpf.c * and
300+ * example3.bpf.c * individually and then statically links respective object
301+ files into the final BPF ELF object file *example.bpf.o *.
272302
273303**$ bpftool gen skeleton example.bpf.o name example | tee example.skel.h **
274304
@@ -291,7 +321,15 @@ BPF ELF object file *example.bpf.o*.
291321 struct bpf_map *data;
292322 struct bpf_map *bss;
293323 struct bpf_map *my_map;
324+ struct bpf_map *testmod_map;
294325 } maps;
326+ struct {
327+ struct example__testmod_map__bpf_testmod_ops {
328+ const struct bpf_program *test_1;
329+ const struct bpf_program *test_2;
330+ int data;
331+ } *testmod_map;
332+ } struct_ops;
295333 struct {
296334 struct bpf_program *handle_sys_enter;
297335 struct bpf_program *handle_sys_exit;
@@ -304,6 +342,7 @@ BPF ELF object file *example.bpf.o*.
304342 struct {
305343 int x;
306344 } data;
345+ int test_2_result;
307346 } *bss;
308347 struct example__data {
309348 _Bool global_flag;
@@ -342,10 +381,16 @@ BPF ELF object file *example.bpf.o*.
342381
343382 skel->rodata->param1 = 128;
344383
384+ /* Change the value through the pointer of shadow type */
385+ skel->struct_ops.testmod_map->data = 13;
386+
345387 err = example__load(skel);
346388 if (err)
347389 goto cleanup;
348390
391+ /* The result of the function test_2() */
392+ printf("test_2_result: %d\n", skel->bss->test_2_result);
393+
349394 err = example__attach(skel);
350395 if (err)
351396 goto cleanup;
@@ -372,6 +417,7 @@ BPF ELF object file *example.bpf.o*.
372417
373418::
374419
420+ test_2_result: 17
375421 my_map name: my_map
376422 sys_enter prog FD: 8
377423 my_static_var: 7
0 commit comments