High-level Fentry/Fexit DSL for BPF programs.
Fentry (function entry) and Fexit (function exit) programs are modern BPF tracing programs that attach to kernel functions using BPF trampolines. They provide typed access to function arguments via BTF (BPF Type Format).
Advantages over kprobes:
Fentry/Fexit programs receive arguments directly:
Example: (deffentry-instructions trace-tcp-connect {:function "tcp_v4_connect" :args [:sk :addr :addr-len]} ;; sk is in r1, addr in r2, addr-len in r3 [])
High-level Fentry/Fexit DSL for BPF programs.
Fentry (function entry) and Fexit (function exit) programs are
modern BPF tracing programs that attach to kernel functions using
BPF trampolines. They provide typed access to function arguments
via BTF (BPF Type Format).
Advantages over kprobes:
- Lower overhead (no software breakpoints)
- Typed arguments via BTF
- Fexit can access both arguments and return value
- Better verifier support
Fentry/Fexit programs receive arguments directly:
- r1-r5: Function arguments (up to 5)
- Fexit: r0 contains return value at exit
Example:
(deffentry-instructions trace-tcp-connect
{:function "tcp_v4_connect"
:args [:sk :addr :addr-len]}
;; sk is in r1, addr in r2, addr-len in r3
[])(arg-reg arg-index)Get the register containing a function argument.
Parameters:
Returns register keyword (:r1 through :r5).
Example: (arg-reg 0) ;; => :r1 (first argument) (arg-reg 2) ;; => :r3 (third argument)
Get the register containing a function argument. Parameters: - arg-index: 0-based argument index (0-4) Returns register keyword (:r1 through :r5). Example: (arg-reg 0) ;; => :r1 (first argument) (arg-reg 2) ;; => :r3 (third argument)
Register mapping for function arguments. In fentry/fexit, arguments are passed directly in r1-r5.
Register mapping for function arguments. In fentry/fexit, arguments are passed directly in r1-r5.
(build-fentry-program {:keys [arg-saves body return-value]
:or {arg-saves [] return-value 0}})Build a complete fentry program with standard structure.
Parameters:
Returns assembled program bytes.
Example: (build-fentry-program {:arg-saves [[0 :r6] [1 :r7]] :body [(dsl/mov :r0 42)] :return-value 0})
Build a complete fentry program with standard structure.
Parameters:
- opts: Map with:
:arg-saves - Vector of [arg-index dest-reg] pairs (optional)
:body - Vector of body instructions
:return-value - Value to return (default 0)
Returns assembled program bytes.
Example:
(build-fentry-program
{:arg-saves [[0 :r6] [1 :r7]]
:body [(dsl/mov :r0 42)]
:return-value 0})(build-fexit-program {:keys [arg-saves ret-reg body return-value]
:or {arg-saves [] return-value 0}})Build a complete fexit program with standard structure.
Parameters:
Returns assembled program bytes.
Example: (build-fexit-program {:arg-saves [[0 :r6]] :ret-reg :r7 :body [(dsl/mov :r0 0)] :return-value 0})
Build a complete fexit program with standard structure.
Parameters:
- opts: Map with:
:arg-saves - Vector of [arg-index dest-reg] pairs (optional)
:ret-reg - Register to save return value (optional)
:body - Vector of body instructions
:return-value - Value to return (default 0)
Returns assembled program bytes.
Example:
(build-fexit-program
{:arg-saves [[0 :r6]]
:ret-reg :r7
:body [(dsl/mov :r0 0)]
:return-value 0})(deffentry-instructions fn-name options & body)Define a fentry program as a function returning instructions.
Parameters:
Example: (deffentry-instructions trace-tcp-connect {:function "tcp_v4_connect" :args [:sk :addr :addr-len] :arg-saves [[0 :r6] [1 :r7]]} ;; r6 = sk, r7 = addr [])
Define a fentry program as a function returning instructions.
Parameters:
- fn-name: Name for the defined function
- options: Map with:
:function - Kernel function name to trace
:args - Vector of argument names (for documentation)
:arg-saves - Vector of [arg-index dest-reg] pairs (optional)
- body: Body expressions (should return vectors of instructions)
Example:
(deffentry-instructions trace-tcp-connect
{:function "tcp_v4_connect"
:args [:sk :addr :addr-len]
:arg-saves [[0 :r6] [1 :r7]]}
;; r6 = sk, r7 = addr
[])(deffexit-instructions fn-name options & body)Define a fexit program as a function returning instructions.
Parameters:
Example: (deffexit-instructions trace-tcp-connect-exit {:function "tcp_v4_connect" :args [:sk :addr :addr-len] :arg-saves [[0 :r6]] :ret-reg :r7} ;; r6 = sk, r7 = return value [])
Define a fexit program as a function returning instructions.
Parameters:
- fn-name: Name for the defined function
- options: Map with:
:function - Kernel function name to trace
:args - Vector of argument names (for documentation)
:arg-saves - Vector of [arg-index dest-reg] pairs (optional)
:ret-reg - Register to save return value (optional)
- body: Body expressions (should return vectors of instructions)
Example:
(deffexit-instructions trace-tcp-connect-exit
{:function "tcp_v4_connect"
:args [:sk :addr :addr-len]
:arg-saves [[0 :r6]]
:ret-reg :r7}
;; r6 = sk, r7 = return value
[])(describe-fentry-trampoline func-name attach-type)Return information about fentry/fexit attachment.
This is informational only - actual attachment is done through the BPF syscall with BTF ID.
Parameters:
Returns map describing the trampoline setup.
Return information about fentry/fexit attachment. This is informational only - actual attachment is done through the BPF syscall with BTF ID. Parameters: - func-name: Kernel function name - attach-type: :fentry, :fexit, or :fmod-ret Returns map describing the trampoline setup.
BPF attach types for fentry/fexit.
BPF attach types for fentry/fexit.
(fentry-filter-by-comm comm-buf-offset target-comm skip-offset)Generate instructions to filter by process name.
Requires stack space for 16-byte comm buffer.
Parameters:
Returns vector of instructions.
Example: (fentry-filter-by-comm -16 "myprocess" 2)
Generate instructions to filter by process name. Requires stack space for 16-byte comm buffer. Parameters: - comm-buf-offset: Stack offset for 16-byte buffer - target-comm: Target process name (first 8 bytes compared) - skip-offset: Number of instructions to skip if comm doesn't match Returns vector of instructions. Example: (fentry-filter-by-comm -16 "myprocess" 2)
(fentry-filter-by-pid target-pid skip-offset)Generate instructions to filter by PID.
Parameters:
Returns vector of instructions.
Example: (fentry-filter-by-pid 1234 2) ;; If current PID != 1234, skip 2 instructions
Generate instructions to filter by PID. Parameters: - target-pid: PID to filter for - skip-offset: Number of instructions to skip if PID doesn't match Returns vector of instructions. Example: (fentry-filter-by-pid 1234 2) ;; If current PID != 1234, skip 2 instructions
(fentry-ktime-get-ns)Generate instruction to get current kernel time in nanoseconds.
Returns call instruction that puts timestamp in r0.
Example: (fentry-ktime-get-ns) ;; r0 = ktime_get_ns()
Generate instruction to get current kernel time in nanoseconds. Returns call instruction that puts timestamp in r0. Example: (fentry-ktime-get-ns) ;; r0 = ktime_get_ns()
(fentry-log-comm buf-reg)Generate instructions to get current task comm (process name).
Parameters:
Returns vector of instructions.
Example: (fentry-log-comm :r1) ;; Calls bpf_get_current_comm(buf, 16)
Generate instructions to get current task comm (process name). Parameters: - buf-reg: Register pointing to 16-byte buffer on stack Returns vector of instructions. Example: (fentry-log-comm :r1) ;; Calls bpf_get_current_comm(buf, 16)
(fentry-log-pid)Generate instructions to get and log current PID.
Returns vector of instructions that gets PID into r0.
Example: (fentry-log-pid) ;; Calls bpf_get_current_pid_tgid
Generate instructions to get and log current PID. Returns vector of instructions that gets PID into r0. Example: (fentry-log-pid) ;; Calls bpf_get_current_pid_tgid
BPF program types for fentry/fexit.
BPF program types for fentry/fexit.
(fentry-prologue arg-saves)Generate standard fentry prologue instructions.
Saves specified arguments to callee-saved registers for use throughout the program.
Parameters:
Returns vector of mov instructions.
Example: (fentry-prologue [[0 :r6] [1 :r7]]) ;; Generates: ;; mov r6, r1 ; Save first arg ;; mov r7, r2 ; Save second arg
Generate standard fentry prologue instructions. Saves specified arguments to callee-saved registers for use throughout the program. Parameters: - arg-saves: Vector of [arg-index dest-reg] pairs Returns vector of mov instructions. Example: (fentry-prologue [[0 :r6] [1 :r7]]) ;; Generates: ;; mov r6, r1 ; Save first arg ;; mov r7, r2 ; Save second arg
(fentry-return value)Generate instructions to return a value from fentry/fexit.
Parameters:
Returns vector of [mov, exit] instructions.
Example: (fentry-return 0)
Generate instructions to return a value from fentry/fexit. Parameters: - value: Return value (typically 0) Returns vector of [mov, exit] instructions. Example: (fentry-return 0)
(fentry-save-args arg-count)Generate instructions to save all specified arguments.
Simplified interface - saves args 0..n to registers starting at :r6.
Parameters:
Returns vector of mov instructions.
Example: (fentry-save-args 3) ;; Generates: ;; mov r6, r1 ; arg0 ;; mov r7, r2 ; arg1 ;; mov r8, r3 ; arg2
Generate instructions to save all specified arguments. Simplified interface - saves args 0..n to registers starting at :r6. Parameters: - arg-count: Number of arguments to save (1-5) Returns vector of mov instructions. Example: (fentry-save-args 3) ;; Generates: ;; mov r6, r1 ; arg0 ;; mov r7, r2 ; arg1 ;; mov r8, r3 ; arg2
(fentry-section-name func-name)Generate ELF section name for fentry program.
Parameters:
Returns section name like "fentry/tcp_v4_connect"
Example: (fentry-section-name "tcp_v4_connect") ;; => "fentry/tcp_v4_connect"
Generate ELF section name for fentry program. Parameters: - func-name: Kernel function name Returns section name like "fentry/tcp_v4_connect" Example: (fentry-section-name "tcp_v4_connect") ;; => "fentry/tcp_v4_connect"
(fexit-get-return-value dst-reg)Generate instruction to save return value in fexit program.
In fexit programs, after the function returns, the return value is available. We need to access it through the context.
Note: The actual mechanism depends on the kernel version and whether the function has a return value.
Parameters:
Returns vector of instructions.
Example: (fexit-get-return-value :r6) ;; Saves return value to r6
Generate instruction to save return value in fexit program. In fexit programs, after the function returns, the return value is available. We need to access it through the context. Note: The actual mechanism depends on the kernel version and whether the function has a return value. Parameters: - dst-reg: Destination register for return value Returns vector of instructions. Example: (fexit-get-return-value :r6) ;; Saves return value to r6
(fexit-section-name func-name)Generate ELF section name for fexit program.
Parameters:
Returns section name like "fexit/tcp_v4_connect"
Example: (fexit-section-name "tcp_v4_connect") ;; => "fexit/tcp_v4_connect"
Generate ELF section name for fexit program. Parameters: - func-name: Kernel function name Returns section name like "fexit/tcp_v4_connect" Example: (fexit-section-name "tcp_v4_connect") ;; => "fexit/tcp_v4_connect"
(fmod-ret-section-name func-name)Generate ELF section name for fmod_ret program.
Parameters:
Returns section name like "fmod_ret/func_name"
Example: (fmod-ret-section-name "security_bprm_check") ;; => "fmod_ret/security_bprm_check"
Generate ELF section name for fmod_ret program. Parameters: - func-name: Kernel function name Returns section name like "fmod_ret/func_name" Example: (fmod-ret-section-name "security_bprm_check") ;; => "fmod_ret/security_bprm_check"
(get-arg-by-name btf func-name param-name)Get argument index by parameter name.
Parameters:
Returns 0-based argument index or nil if not found.
Example: (get-arg-by-name btf "tcp_v4_connect" :sk) ;; => 0
Get argument index by parameter name. Parameters: - btf: BTF data - func-name: Kernel function name - param-name: Parameter name (string or keyword) Returns 0-based argument index or nil if not found. Example: (get-arg-by-name btf "tcp_v4_connect" :sk) ;; => 0
(get-arg-type btf func-name arg-index)Get the BTF type of a function argument.
Parameters:
Returns BTF type info or nil.
Example: (get-arg-type btf "tcp_v4_connect" 0) ;; Returns type info for first argument
Get the BTF type of a function argument. Parameters: - btf: BTF data - func-name: Kernel function name - arg-index: 0-based argument index Returns BTF type info or nil. Example: (get-arg-type btf "tcp_v4_connect" 0) ;; Returns type info for first argument
(get-return-type btf func-name)Get the BTF return type of a function.
Parameters:
Returns BTF type info or nil.
Example: (get-return-type btf "tcp_v4_connect") ;; Returns type info for return type
Get the BTF return type of a function. Parameters: - btf: BTF data - func-name: Kernel function name Returns BTF type info or nil. Example: (get-return-type btf "tcp_v4_connect") ;; Returns type info for return type
(make-fentry-program-info program-name func-name instructions)Create program metadata for a fentry program.
Parameters:
Returns map with program metadata.
Create program metadata for a fentry program. Parameters: - program-name: Name for the BPF program - func-name: Kernel function to trace - instructions: Program instructions Returns map with program metadata.
(make-fexit-program-info program-name func-name instructions)Create program metadata for a fexit program.
Parameters:
Returns map with program metadata.
Create program metadata for a fexit program. Parameters: - program-name: Name for the BPF program - func-name: Kernel function to trace - instructions: Program instructions Returns map with program metadata.
(make-fmod-ret-program-info program-name func-name instructions)Create program metadata for a fmod_ret program.
fmod_ret (modify return) programs can modify the return value of certain allowlisted kernel functions.
Parameters:
Returns map with program metadata.
Create program metadata for a fmod_ret program. fmod_ret (modify return) programs can modify the return value of certain allowlisted kernel functions. Parameters: - program-name: Name for the BPF program - func-name: Kernel function to trace - instructions: Program instructions Returns map with program metadata.
(read-nested-field btf src-reg type-id field-path dst-reg tmp-reg)Generate instructions to read a nested struct field.
Uses BTF to determine the correct offset.
Parameters:
Returns vector of instructions.
Example: (read-nested-field btf :r6 sock-type-id [:sk_common :skc_daddr] :r0 :r1)
Generate instructions to read a nested struct field. Uses BTF to determine the correct offset. Parameters: - btf: BTF data - src-reg: Register containing pointer to outer struct - type-id: BTF type ID of the struct - field-path: Vector of field names (keywords or strings) - dst-reg: Destination register - tmp-reg: Temporary register for intermediate pointers Returns vector of instructions. Example: (read-nested-field btf :r6 sock-type-id [:sk_common :skc_daddr] :r0 :r1)
(read-struct-field src-reg offset dst-reg size)Generate instructions to read a field from a struct pointer.
Parameters:
Returns vector of ldx instruction.
Example: (read-struct-field :r6 16 :r0 8) ;; ldxdw r0, [r6 + 16]
Generate instructions to read a field from a struct pointer. Parameters: - src-reg: Register containing pointer to struct - offset: Field offset in bytes - dst-reg: Destination register - size: Size in bytes (1, 2, 4, or 8) Returns vector of ldx instruction. Example: (read-struct-field :r6 16 :r0 8) ;; ldxdw r0, [r6 + 16]
(resolve-btf-function btf func-name)Resolve function information from BTF.
Parameters:
Returns map with:
Returns nil if function not found.
Resolve function information from BTF. Parameters: - btf: BTF data (from btf/load-btf-file) - func-name: Kernel function name Returns map with: - :func - Function BTF info - :proto - Function prototype info - :params - Vector of parameter info with names - :return-type - Return type ID Returns nil if function not found.
(suggest-arg-saves btf func-name)Suggest arg-saves configuration for a function.
Parameters:
Returns suggested arg-saves vector.
Example: (suggest-arg-saves btf "tcp_v4_connect") ;; => [[0 :r6] [1 :r7] [2 :r8]]
Suggest arg-saves configuration for a function. Parameters: - btf: BTF data - func-name: Kernel function name Returns suggested arg-saves vector. Example: (suggest-arg-saves btf "tcp_v4_connect") ;; => [[0 :r6] [1 :r7] [2 :r8]]
(validate-fentry-target btf func-name)Validate that a function can be targeted by fentry/fexit.
Parameters:
Returns map with:
Validate that a function can be targeted by fentry/fexit. Parameters: - btf: BTF data (from btf/load-btf-file) - func-name: Kernel function name Returns map with: - :valid? - true if function exists in BTF - :func-info - Function BTF info if found - :param-count - Number of parameters - :error - Error message if invalid
cljdoc builds & hosts documentation for Clojure/Script libraries
| Ctrl+k | Jump to recent docs |
| ← | Move to previous article |
| → | Move to next article |
| Ctrl+/ | Jump to the search field |