Prepare to handle skb dynptrs for accessing the metadata area. Code move. No observable changes. Signed-off-by: Jakub Sitnicki --- include/linux/filter.h | 25 ++++++++++++++++++------- kernel/bpf/helpers.c | 9 +++------ net/core/filter.c | 38 +++++++++++++++++++++++++++----------- 3 files changed, 48 insertions(+), 24 deletions(-) diff --git a/include/linux/filter.h b/include/linux/filter.h index eca229752cbe..468d83604241 100644 --- a/include/linux/filter.h +++ b/include/linux/filter.h @@ -1764,27 +1764,38 @@ static __always_inline long __bpf_xdp_redirect_map(struct bpf_map *map, u64 inde } #ifdef CONFIG_NET -int __bpf_skb_load_bytes(const struct sk_buff *skb, u32 offset, void *to, u32 len); -int __bpf_skb_store_bytes(struct sk_buff *skb, u32 offset, const void *from, - u32 len, u64 flags); +int bpf_dynptr_skb_read(const struct bpf_dynptr_kern *src, u32 offset, + void *dst, u32 len); +int bpf_dynptr_skb_write(const struct bpf_dynptr_kern *dst, u32 offset, + const void *src, u32 len, u64 flags); +void *bpf_dynptr_skb_slice(const struct bpf_dynptr_kern *ptr, u32 offset, + void *buf, u32 len); int __bpf_xdp_load_bytes(struct xdp_buff *xdp, u32 offset, void *buf, u32 len); int __bpf_xdp_store_bytes(struct xdp_buff *xdp, u32 offset, void *buf, u32 len); void *bpf_xdp_pointer(struct xdp_buff *xdp, u32 offset, u32 len); void bpf_xdp_copy_buf(struct xdp_buff *xdp, unsigned long off, void *buf, unsigned long len, bool flush); #else /* CONFIG_NET */ -static inline int __bpf_skb_load_bytes(const struct sk_buff *skb, u32 offset, - void *to, u32 len) +static inline int bpf_dynptr_skb_read(const struct bpf_dynptr_kern *src, + u32 offset, void *dst, u32 len) { return -EOPNOTSUPP; } -static inline int __bpf_skb_store_bytes(struct sk_buff *skb, u32 offset, - const void *from, u32 len, u64 flags) +static inline int bpf_dynptr_skb_write(const struct bpf_dynptr_kern *dst, + u32 offset, const void *src, u32 len, + u64 flags); { return -EOPNOTSUPP; } +static inline void *bpf_dynptr_skb_slice(const struct bpf_dynptr_kern *ptr, + u32 offset, void *buf, u32 len); + +{ + return NULL; +} + static inline int __bpf_xdp_load_bytes(struct xdp_buff *xdp, u32 offset, void *buf, u32 len) { diff --git a/kernel/bpf/helpers.c b/kernel/bpf/helpers.c index 40c18b37ab05..da9c6ccd7cd7 100644 --- a/kernel/bpf/helpers.c +++ b/kernel/bpf/helpers.c @@ -1776,7 +1776,7 @@ static int __bpf_dynptr_read(void *dst, u32 len, const struct bpf_dynptr_kern *s memmove(dst, src->data + src->offset + offset, len); return 0; case BPF_DYNPTR_TYPE_SKB: - return __bpf_skb_load_bytes(src->data, offset, dst, len); + return bpf_dynptr_skb_read(src, offset, dst, len); case BPF_DYNPTR_TYPE_XDP: return __bpf_xdp_load_bytes(src->data, src->offset + offset, dst, len); default: @@ -1829,7 +1829,7 @@ int __bpf_dynptr_write(const struct bpf_dynptr_kern *dst, u32 offset, void *src, memmove(dst->data + dst->offset + offset, src, len); return 0; case BPF_DYNPTR_TYPE_SKB: - return __bpf_skb_store_bytes(dst->data, offset, src, len, flags); + return bpf_dynptr_skb_write(dst, offset, src, len, flags); case BPF_DYNPTR_TYPE_XDP: if (flags) return -EINVAL; @@ -2693,10 +2693,7 @@ __bpf_kfunc void *bpf_dynptr_slice(const struct bpf_dynptr *p, u32 offset, case BPF_DYNPTR_TYPE_RINGBUF: return ptr->data + ptr->offset + offset; case BPF_DYNPTR_TYPE_SKB: - if (buffer__opt) - return skb_header_pointer(ptr->data, offset, len, buffer__opt); - else - return skb_pointer_if_linear(ptr->data, offset, len); + return bpf_dynptr_skb_slice(ptr, offset, buffer__opt, len); case BPF_DYNPTR_TYPE_XDP: { void *xdp_ptr = bpf_xdp_pointer(ptr->data, ptr->offset + offset, len); diff --git a/net/core/filter.c b/net/core/filter.c index 7a72f766aacf..1fee51b72220 100644 --- a/net/core/filter.c +++ b/net/core/filter.c @@ -1736,12 +1736,6 @@ static const struct bpf_func_proto bpf_skb_store_bytes_proto = { .arg5_type = ARG_ANYTHING, }; -int __bpf_skb_store_bytes(struct sk_buff *skb, u32 offset, const void *from, - u32 len, u64 flags) -{ - return ____bpf_skb_store_bytes(skb, offset, from, len, flags); -} - BPF_CALL_4(bpf_skb_load_bytes, const struct sk_buff *, skb, u32, offset, void *, to, u32, len) { @@ -1772,11 +1766,6 @@ static const struct bpf_func_proto bpf_skb_load_bytes_proto = { .arg4_type = ARG_CONST_SIZE, }; -int __bpf_skb_load_bytes(const struct sk_buff *skb, u32 offset, void *to, u32 len) -{ - return ____bpf_skb_load_bytes(skb, offset, to, len); -} - BPF_CALL_4(bpf_flow_dissector_load_bytes, const struct bpf_flow_dissector *, ctx, u32, offset, void *, to, u32, len) @@ -11978,6 +11967,33 @@ bpf_sk_base_func_proto(enum bpf_func_id func_id, const struct bpf_prog *prog) return func; } +int bpf_dynptr_skb_read(const struct bpf_dynptr_kern *src, u32 offset, + void *dst, u32 len) +{ + const struct sk_buff *skb = src->data; + + return ____bpf_skb_load_bytes(skb, offset, dst, len); +} + +int bpf_dynptr_skb_write(const struct bpf_dynptr_kern *dst, u32 offset, + const void *src, u32 len, u64 flags) +{ + struct sk_buff *skb = dst->data; + + return ____bpf_skb_store_bytes(skb, offset, src, len, flags); +} + +void *bpf_dynptr_skb_slice(const struct bpf_dynptr_kern *ptr, u32 offset, + void *buf, u32 len) +{ + const struct sk_buff *skb = ptr->data; + + if (buf) + return skb_header_pointer(skb, offset, len, buf); + else + return skb_pointer_if_linear(skb, offset, len); +} + __bpf_kfunc_start_defs(); __bpf_kfunc int bpf_dynptr_from_skb(struct __sk_buff *s, u64 flags, struct bpf_dynptr *ptr__uninit) -- 2.43.0