2

I've seen that for each type of ebpf program there is a different input (context) to the program. For example in the case of a BPF_PROG_TYPE_SOCKET_FILTER program a pointer to struct __sk_buff is passed as an argument. Where are defined the contexts for each program type ?

pchaigno
  • 11,313
  • 2
  • 29
  • 54
Maicake
  • 1,046
  • 10
  • 34

1 Answers1

5

Where are defined the contexts for each program type?

There are defined in the kernel, generally in the kernel headers. The precise location depends on the program type. For example, __sk_buff is used by several program types and is defined in linux/bpf.h.

To find which context each program is expecting, you can look at BPF samples in the kernel or try to find the xxxx_convert_ctx_access for a given program type. These functions translate accesses to the context object into accesses to the actual kernel object (for example, __sk_buff is a mirror to sk_buff). As an example, XDP programs expect a context of type struct xdp_md.

As pointed out by @Qeole in comments, there's a blog post by Oracle, from January 2019, that lists the expected context for each program type.

pchaigno
  • 11,313
  • 2
  • 29
  • 54
  • 2
    Good answer. As a complement, [this blog post](https://blogs.oracle.com/linux/notes-on-bpf-1) lists the contexts for all the (then existing) program types and may be of interest. – Qeole Aug 27 '19 at 12:50
  • Ah, great! I've added it to the answer. Thanks! – pchaigno Aug 27 '19 at 13:01
  • In the article about BPF_PROG_TYPE_TRACEPOINT it's written "What context is provided? The context provided by the specific tracepoint; arguments and data types are associated with the tracepoint definition." Within /include/trace/events/syscalls.h there is TRACE_EVENT_FN(sys_enter, TP_PROTO(struct pt_regs *regs, long id), TP_ARGS(regs, id), TP_STRUCT__entry( __field( long, id ) __array( unsigned long, args, 6 ) ), .... Ho can I exactly understand which is the context? – Maicake Aug 27 '19 at 15:06
  • And also. I've seen here https://github.com/torvalds/linux/blob/06821504fd47a5e5b641aeeb638a0ae10a216ef8/tools/include/uapi/linux/bpf.h#L3430-L3432 there is bpf_raw_tracepoint_args defined which is used with raw_tracepoint programs. But I can't find the context for just tracepoint . – Maicake Aug 27 '19 at 15:10
  • 1
    For tracepoints, the context structure is specific to each probe site (e.g., `block:block_getrq` and `block:block_plug` will have different context structures). See [this StackOverflow answer](https://stackoverflow.com/a/47031794/6884590) for how to get the content of each structure. You will have to declare that structure yourself with the appropriate fields (though [bcc does that for you](https://github.com/iovisor/bcc/blob/270d54ae18c589b352dad71f465cf7d439275e24/src/cc/frontends/clang/tp_frontend_action.cc#L137)). – pchaigno Aug 27 '19 at 15:44
  • Thanks a lot, after looking around I was reading that in this example https://github.com/torvalds/linux/blob/master/samples/bpf/xdp_redirect_cpu_kern.c#L572-L584. Anyway I'd like to understand how I can build the structure starting from the format output. In my case the output of /sys/kernel/debug/tracing/events/syscalls/sys_enter_open/format . Because usually I don't see a 1 to 1 mapping , as I've seen between this /sys/kernel/debug/tracing/events/power/cpu_idle/format (6 fields) and https://github.com/torvalds/linux/blob/master/samples/bpf/cpustat_kern.c (here the struct has 3 fields) – Maicake Aug 28 '19 at 10:18