diff --git a/ebpf/aya-ebpf/src/programs/sk_buff.rs b/ebpf/aya-ebpf/src/programs/sk_buff.rs index caca717f3..b69ae5278 100644 --- a/ebpf/aya-ebpf/src/programs/sk_buff.rs +++ b/ebpf/aya-ebpf/src/programs/sk_buff.rs @@ -86,6 +86,10 @@ impl SkBuff { let len = usize::try_from(self.len()).map_err(|core::num::TryFromIntError { .. }| -1)?; let len = len.checked_sub(offset).ok_or(-1)?; let len = len.min(dst.len()); + if len == 0 { + return Ok(0); + } + let len_u32 = u32::try_from(len).map_err(|core::num::TryFromIntError { .. }| -1)?; let ret = unsafe { bpf_skb_load_bytes( diff --git a/test/integration-ebpf/src/test.rs b/test/integration-ebpf/src/test.rs index ab3da99db..ab1ad0120 100644 --- a/test/integration-ebpf/src/test.rs +++ b/test/integration-ebpf/src/test.rs @@ -5,11 +5,12 @@ use aya_ebpf::{ bindings::{bpf_ret_code, xdp_action}, macros::{ - flow_dissector, kprobe, kretprobe, lsm, lsm_cgroup, tracepoint, uprobe, uretprobe, xdp, + flow_dissector, kprobe, kretprobe, lsm, lsm_cgroup, socket_filter, tracepoint, uprobe, + uretprobe, xdp, }, programs::{ - FlowDissectorContext, LsmContext, ProbeContext, RetProbeContext, TracePointContext, - XdpContext, + FlowDissectorContext, LsmContext, ProbeContext, RetProbeContext, SkBuffContext, + TracePointContext, XdpContext, }, }; #[cfg(not(test))] @@ -61,3 +62,12 @@ const fn test_lsm(_ctx: LsmContext) -> i32 { const fn test_lsm_cgroup(_ctx: LsmContext) -> i32 { 0 // Disallow. } + +#[socket_filter] +fn fix_test_load_bytes(ctx: SkBuffContext) -> i64 { + let mut buf = [0u8; 4]; + match ctx.load_bytes(2, &mut buf) { + Ok(_) => 1, + Err(_) => 0, + } +} diff --git a/test/integration-test/src/tests.rs b/test/integration-test/src/tests.rs index da995bfa0..11dd43845 100644 --- a/test/integration-test/src/tests.rs +++ b/test/integration-test/src/tests.rs @@ -18,6 +18,7 @@ mod info; mod iter; mod linear_data_structures; mod load; +mod load_bytes; mod log; mod lsm; mod map_pin; diff --git a/test/integration-test/src/tests/load_bytes.rs b/test/integration-test/src/tests/load_bytes.rs new file mode 100644 index 000000000..a3c6c2f58 --- /dev/null +++ b/test/integration-test/src/tests/load_bytes.rs @@ -0,0 +1,24 @@ +use aya::{ + Ebpf, + programs::{ProgramType, SocketFilter}, + sys::is_program_supported, +}; + +// Load the eBPF socket filter program from the embedded bytes and ensure it loads +// successfully (i.e., passes verification) using Ebpf::load and prog.load(). +#[test_log::test] +fn test_load_bytes() { + if !is_program_supported(ProgramType::SocketFilter).unwrap() { + eprintln!("skipping test - socket_filter program not supported"); + return; + } + + let mut bpf: Ebpf = Ebpf::load(crate::TEST).unwrap(); + let prog: &mut SocketFilter = bpf + .program_mut("fix_test_load_bytes") + .unwrap() + .try_into() + .unwrap(); + prog.load().unwrap(); + // should pass verification +}