C Fundamentals
BPF C Specifics
BPF-specific C features and pitfalls - __attribute__ syntax, const/volatile restrictions, offsetof, and a summary of BPF C pitfalls.
1.13 __attribute__ Syntax (GCC/Clang Extensions)
Commonly used compiler attributes in BPF code:
// Mandatory inlining (required in BPF)
static __always_inline int foo(void) { }
// Compile even if unused (part of the SEC macro)
__attribute__((section("xdp"), used))
// Remove struct padding
__attribute__((packed))
// Force alignment
__attribute__((aligned(8)))
How the SEC() macro works:
#define SEC(NAME) __attribute__((section(NAME), used))
SEC("xdp")
int xdp_prog(struct xdp_md *ctx) { ... }
SEC() examples used in eBPFHub:
SEC("tp/sched/sched_process_exec")-> tracepointSEC("tracepoint/syscalls/sys_enter_read")-> syscall entrySEC("kprobe/tcp_finish_connect")-> kprobe
1.14 const, volatile, and restrict
const-> immutablevolatile-> tells the optimizer “this may change”restrict-> pointer aliasing hint
Restrictions in BPF:
constcan cause issues in BPF (verifier)volatileis sometimes needed for map access- Global const string/array is FORBIDDEN (relocation issue)
// WRONG (does not work in BPF)
const char *msg = "hello";
// CORRECT
char msg[] = "hello"; // on the stack
1.15 offsetof Macro
Calculate the offset of a struct member at compile time:
#include <stddef.h>
struct iphdr {
// ...
__be32 saddr; // offset: 12
__be32 daddr; // offset: 16
};
size_t off = offsetof(struct iphdr, saddr); // = 12
Usage in BPF:
bpf_skb_store_bytes(skb,
l3_off + offsetof(struct iphdr, saddr),
&new_saddr, 4, 0);
1.16 BPF C Pitfalls Summary
| Rule | Reason |
|---|---|
Every function must be static __always_inline | No normal calls in BPF (except kernel 4.16+ bpf-to-bpf) |
| NO global variables | Relocation issue |
| NO const strings | Relocation issue |
| NO unbounded loops | Verifier rejects them |
Use __builtin_* for memset/memcpy | No standard library |
| Watch out for struct padding | Verifier stack check |
| Pointer bounds check is MANDATORY | if (ptr + 1 > data_end) |
eBPFHub: In all exercises, these rules come up in practice - especially NULL checks, bounded loops, and stack buffer sizes.
Exercise: Write a simple BPF program, apply these rules, and pass the verifier.