#define __PT_RET_REG u_regs[UREG_I7] #define __PT_FP_REG __unsupported__ #define __PT_RC_REG u_regs[UREG_I0] #define __PT_SP_REG u_regs[UREG_FP] /* Should this also be a bpf_target check for the sparc case? */ #ifdefined(__arch64__) #define __PT_IP_REG tpc #else #define __PT_IP_REG pc #endif
/* allow some architectures to override `struct pt_regs` */ #ifndef __PT_REGS_CAST #define __PT_REGS_CAST(x) (x) #endif
/* * Different architectures support different number of arguments passed * through registers. i386 supports just 3, some arches support up to 8.
*/ #ifndef __PT_PARM4_REG #define __PT_PARM4_REG __unsupported__ #endif #ifndef __PT_PARM5_REG #define __PT_PARM5_REG __unsupported__ #endif #ifndef __PT_PARM6_REG #define __PT_PARM6_REG __unsupported__ #endif #ifndef __PT_PARM7_REG #define __PT_PARM7_REG __unsupported__ #endif #ifndef __PT_PARM8_REG #define __PT_PARM8_REG __unsupported__ #endif /* * Similarly, syscall-specific conventions might differ between function call * conventions within each architecture. All supported architectures pass * either 6 or 7 syscall arguments in registers. * * See syscall(2) manpage for succinct table with information on each arch.
*/ #ifndef __PT_PARM7_SYSCALL_REG #define __PT_PARM7_SYSCALL_REG __unsupported__ #endif
/* * When invoked from a syscall handler kprobe, returns a pointer to a * struct pt_regs containing syscall arguments and suitable for passing to * PT_REGS_PARMn_SYSCALL() and PT_REGS_PARMn_CORE_SYSCALL().
*/ #ifndef PT_REGS_SYSCALL_REGS /* By default, assume that the arch selects ARCH_HAS_SYSCALL_WRAPPER. */ #define PT_REGS_SYSCALL_REGS(ctx) ((struct pt_regs *)PT_REGS_PARM1(ctx)) #endif
/* * BPF_PROG is a convenience wrapper for generic tp_btf/fentry/fexit and * similar kinds of BPF programs, that accept input arguments as a single * pointer to untyped u64 array, where each u64 can actually be a typed * pointer or integer of different size. Instead of requiring user to write * manual casts and work with array elements by index, BPF_PROG macro * allows user to declare a list of named and typed input arguments in the * same syntax as for normal C function. All the casting is hidden and * performed transparently, while user code can just assume working with * function arguments of specified type and name. * * Original raw context argument is preserved as well as 'ctx' argument. * This is useful when using BPF helpers that expect original context * as one of the parameters (e.g., for bpf_perf_event_output()).
*/ #define BPF_PROG(name, args...) \
name(unsignedlonglong *ctx); \ static __always_inline typeof(name(0)) \
____##name(unsignedlonglong *ctx, ##args); \
typeof(name(0)) name(unsignedlonglong *ctx) \
{ \
_Pragma("GCC diagnostic push") \
_Pragma("GCC diagnostic ignored \"-Wint-conversion\"") \ return ____##name(___bpf_ctx_cast(args)); \
_Pragma("GCC diagnostic pop") \
} \ static __always_inline typeof(name(0)) \
____##name(unsignedlonglong *ctx, ##args)
#define ___bpf_ctx_decl0() #define ___bpf_ctx_decl1(t, x) , t x #define ___bpf_ctx_decl2(t, x, args...) , t x ___bpf_ctx_decl1(args) #define ___bpf_ctx_decl3(t, x, args...) , t x ___bpf_ctx_decl2(args) #define ___bpf_ctx_decl4(t, x, args...) , t x ___bpf_ctx_decl3(args) #define ___bpf_ctx_decl5(t, x, args...) , t x ___bpf_ctx_decl4(args) #define ___bpf_ctx_decl6(t, x, args...) , t x ___bpf_ctx_decl5(args) #define ___bpf_ctx_decl7(t, x, args...) , t x ___bpf_ctx_decl6(args) #define ___bpf_ctx_decl8(t, x, args...) , t x ___bpf_ctx_decl7(args) #define ___bpf_ctx_decl9(t, x, args...) , t x ___bpf_ctx_decl8(args) #define ___bpf_ctx_decl10(t, x, args...) , t x ___bpf_ctx_decl9(args) #define ___bpf_ctx_decl11(t, x, args...) , t x ___bpf_ctx_decl10(args) #define ___bpf_ctx_decl12(t, x, args...) , t x ___bpf_ctx_decl11(args) #define ___bpf_ctx_decl(args...) ___bpf_apply(___bpf_ctx_decl, ___bpf_narg2(args))(args)
/* * BPF_PROG2 is an enhanced version of BPF_PROG in order to handle struct * arguments. Since each struct argument might take one or two u64 values * in the trampoline stack, argument type size is needed to place proper number * of u64 values for each argument. Therefore, BPF_PROG2 has different * syntax from BPF_PROG. For example, for the following BPF_PROG syntax: * * int BPF_PROG(test2, int a, int b) { ... } * * the corresponding BPF_PROG2 syntax is: * * int BPF_PROG2(test2, int, a, int, b) { ... } * * where type and the corresponding argument name are separated by comma. * * Use BPF_PROG2 macro if one of the arguments might be a struct/union larger * than 8 bytes: * * int BPF_PROG2(test_struct_arg, struct bpf_testmod_struct_arg_1, a, int, b, * int, c, int, d, struct bpf_testmod_struct_arg_2, e, int, ret) * { * // access a, b, c, d, e, and ret directly * ... * }
*/ #define BPF_PROG2(name, args...) \
name(unsignedlonglong *ctx); \ static __always_inline typeof(name(0)) \
____##name(unsignedlonglong *ctx ___bpf_ctx_decl(args)); \
typeof(name(0)) name(unsignedlonglong *ctx) \
{ \ return ____##name(ctx ___bpf_ctx_arg(args)); \
} \ static __always_inline typeof(name(0)) \
____##name(unsignedlonglong *ctx ___bpf_ctx_decl(args))
/* * BPF_KPROBE serves the same purpose for kprobes as BPF_PROG for * tp_btf/fentry/fexit BPF programs. It hides the underlying platform-specific * low-level way of getting kprobe input arguments from struct pt_regs, and * provides a familiar typed and named function arguments syntax and * semantics of accessing kprobe input parameters. * * Original struct pt_regs* context is preserved as 'ctx' argument. This might * be necessary when using BPF helpers like bpf_perf_event_output().
*/ #define BPF_KPROBE(name, args...) \
name(struct pt_regs *ctx); \ static __always_inline typeof(name(0)) \
____##name(struct pt_regs *ctx, ##args); \
typeof(name(0)) name(struct pt_regs *ctx) \
{ \
_Pragma("GCC diagnostic push") \
_Pragma("GCC diagnostic ignored \"-Wint-conversion\"") \ return ____##name(___bpf_kprobe_args(args)); \
_Pragma("GCC diagnostic pop") \
} \ static __always_inline typeof(name(0)) \
____##name(struct pt_regs *ctx, ##args)
/* * BPF_KRETPROBE is similar to BPF_KPROBE, except, it only provides optional * return value (in addition to `struct pt_regs *ctx`), but no input * arguments, because they will be clobbered by the time probed function * returns.
*/ #define BPF_KRETPROBE(name, args...) \
name(struct pt_regs *ctx); \ static __always_inline typeof(name(0)) \
____##name(struct pt_regs *ctx, ##args); \
typeof(name(0)) name(struct pt_regs *ctx) \
{ \
_Pragma("GCC diagnostic push") \
_Pragma("GCC diagnostic ignored \"-Wint-conversion\"") \ return ____##name(___bpf_kretprobe_args(args)); \
_Pragma("GCC diagnostic pop") \
} \ static __always_inline typeof(name(0)) ____##name(struct pt_regs *ctx, ##args)
/* If kernel doesn't have CONFIG_ARCH_HAS_SYSCALL_WRAPPER, we have to BPF_CORE_READ from pt_regs */ #define ___bpf_syswrap_args0() ctx #define ___bpf_syswrap_args1(x) ___bpf_syswrap_args0(), (unsignedlonglong)PT_REGS_PARM1_CORE_SYSCALL(regs) #define ___bpf_syswrap_args2(x, args...) ___bpf_syswrap_args1(args), (unsignedlonglong)PT_REGS_PARM2_CORE_SYSCALL(regs) #define ___bpf_syswrap_args3(x, args...) ___bpf_syswrap_args2(args), (unsignedlonglong)PT_REGS_PARM3_CORE_SYSCALL(regs) #define ___bpf_syswrap_args4(x, args...) ___bpf_syswrap_args3(args), (unsignedlonglong)PT_REGS_PARM4_CORE_SYSCALL(regs) #define ___bpf_syswrap_args5(x, args...) ___bpf_syswrap_args4(args), (unsignedlonglong)PT_REGS_PARM5_CORE_SYSCALL(regs) #define ___bpf_syswrap_args6(x, args...) ___bpf_syswrap_args5(args), (unsignedlonglong)PT_REGS_PARM6_CORE_SYSCALL(regs) #define ___bpf_syswrap_args7(x, args...) ___bpf_syswrap_args6(args), (unsignedlonglong)PT_REGS_PARM7_CORE_SYSCALL(regs) #define ___bpf_syswrap_args(args...) ___bpf_apply(___bpf_syswrap_args, ___bpf_narg(args))(args)
/* * BPF_KSYSCALL is a variant of BPF_KPROBE, which is intended for * tracing syscall functions, like __x64_sys_close. It hides the underlying * platform-specific low-level way of getting syscall input arguments from * struct pt_regs, and provides a familiar typed and named function arguments * syntax and semantics of accessing syscall input parameters. * * Original struct pt_regs * context is preserved as 'ctx' argument. This might * be necessary when using BPF helpers like bpf_perf_event_output(). * * At the moment BPF_KSYSCALL does not transparently handle all the calling * convention quirks for the following syscalls: * * - mmap(): __ARCH_WANT_SYS_OLD_MMAP. * - clone(): CONFIG_CLONE_BACKWARDS, CONFIG_CLONE_BACKWARDS2 and * CONFIG_CLONE_BACKWARDS3. * - socket-related syscalls: __ARCH_WANT_SYS_SOCKETCALL. * - compat syscalls. * * This may or may not change in the future. User needs to take extra measures * to handle such quirks explicitly, if necessary. * * This macro relies on BPF CO-RE support and virtual __kconfig externs.
*/ #define BPF_KSYSCALL(name, args...) \
name(struct pt_regs *ctx); \ extern _Bool LINUX_HAS_SYSCALL_WRAPPER __kconfig; \ static __always_inline typeof(name(0)) \
____##name(struct pt_regs *ctx, ##args); \
typeof(name(0)) name(struct pt_regs *ctx) \
{ \ struct pt_regs *regs = LINUX_HAS_SYSCALL_WRAPPER \
? (struct pt_regs *)PT_REGS_PARM1(ctx) \
: ctx; \
_Pragma("GCC diagnostic push") \
_Pragma("GCC diagnostic ignored \"-Wint-conversion\"") \ if (LINUX_HAS_SYSCALL_WRAPPER) \ return ____##name(___bpf_syswrap_args(args)); \ else \ return ____##name(___bpf_syscall_args(args)); \
_Pragma("GCC diagnostic pop") \
} \ static __always_inline typeof(name(0)) \
____##name(struct pt_regs *ctx, ##args)
#define BPF_KPROBE_SYSCALL BPF_KSYSCALL
/* BPF_UPROBE and BPF_URETPROBE are identical to BPF_KPROBE and BPF_KRETPROBE, * but are named way less confusingly for SEC("uprobe") and SEC("uretprobe") * use cases.
*/ #define BPF_UPROBE(name, args...) BPF_KPROBE(name, ##args) #define BPF_URETPROBE(name, args...) BPF_KRETPROBE(name, ##args)
#endif
Messung V0.5
¤ Dauer der Verarbeitung: 0.13 Sekunden
(vorverarbeitet)
¤
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.