lists.openwall.net   lists  /  announce  owl-users  owl-dev  john-users  john-dev  passwdqc-users  yescrypt  popa3d-users  /  oss-security  kernel-hardening  musl  sabotage  tlsify  passwords  /  crypt-dev  xvendor  /  Bugtraq  Full-Disclosure  linux-kernel  linux-netdev  linux-ext4  linux-hardening  linux-cve-announce  PHC 
Open Source and information security mailing list archives
 
Hash Suite: Windows password security audit tool. GUI, reports in PDF.
[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Message-Id: <20250422-afabre-traits-010-rfc2-v2-9-92bcc6b146c9@arthurfabre.com>
Date: Tue, 22 Apr 2025 15:23:38 +0200
From: Arthur Fabre <arthur@...hurfabre.com>
To: netdev@...r.kernel.org, bpf@...r.kernel.org
Cc: jakub@...udflare.com, hawk@...nel.org, yan@...udflare.com, 
 jbrandeburg@...udflare.com, thoiland@...hat.com, lbiancon@...hat.com, 
 ast@...nel.org, kuba@...nel.org, edumazet@...gle.com, 
 Arthur Fabre <arthur@...hurfabre.com>
Subject: [PATCH RFC bpf-next v2 09/17] trait: Store traits in sk_buff
 extension

Use a bit in sk_buff to track whether or not an skb stores traits in
it's headroom.

It's tempting to store it in skb_shared_info like the XDP metadata,
but storing it in the skb allows us to more easily handle cases such as
skb clones in a few patches.

(I couldn't find an existing hole to use in sk_buff, so this makes a 4
byte hole... any pointers to a free bit?)

The following patches add support for handful of drivers, in the final
form we'd like to cover all drivers that currently support XDP metadata.

Signed-off-by: Arthur Fabre <arthur@...hurfabre.com>
---
 include/linux/skbuff.h | 11 +++++++++++
 include/net/xdp.h      | 21 +++++++++++++++++++++
 net/core/skbuff.c      |  4 ++++
 3 files changed, 36 insertions(+)

diff --git a/include/linux/skbuff.h b/include/linux/skbuff.h
index 4f325a1733f8be808345424f737df36e06d4cd98..ae569b1b1af83b586e1be6c69439ef74bac38cf3 100644
--- a/include/linux/skbuff.h
+++ b/include/linux/skbuff.h
@@ -39,6 +39,7 @@
 #include <net/net_debug.h>
 #include <net/dropreason-core.h>
 #include <net/netmem.h>
+#include <net/trait.h>
 
 /**
  * DOC: skb checksums
@@ -4835,6 +4836,7 @@ enum skb_ext_id {
 #if IS_ENABLED(CONFIG_MCTP_FLOWS)
 	SKB_EXT_MCTP,
 #endif
+	SKB_EXT_TRAITS,
 	SKB_EXT_NUM, /* must be last */
 };
 
@@ -4949,6 +4951,15 @@ static inline void skb_ext_copy(struct sk_buff *dst, const struct sk_buff *s) {}
 static inline bool skb_has_extensions(struct sk_buff *skb) { return false; }
 #endif /* CONFIG_SKB_EXTENSIONS */
 
+static inline void *skb_traits(const struct sk_buff *skb)
+{
+#ifdef CONFIG_SKB_EXTENSIONS
+	return skb_ext_find(skb, SKB_EXT_TRAITS);
+#else
+	return NULL;
+#endif
+}
+
 static inline void nf_reset_ct(struct sk_buff *skb)
 {
 #if defined(CONFIG_NF_CONNTRACK) || defined(CONFIG_NF_CONNTRACK_MODULE)
diff --git a/include/net/xdp.h b/include/net/xdp.h
index 0da1e87afdebfd4323d1944de65a6d63438209bf..cddd5b147cf81fa8afd820c9aa4b86d78958ac3d 100644
--- a/include/net/xdp.h
+++ b/include/net/xdp.h
@@ -127,6 +127,17 @@ static __always_inline void *xdp_buff_traits(const struct xdp_buff *xdp)
 	return xdp->data_hard_start + _XDP_FRAME_SIZE;
 }
 
+static __always_inline void __xdp_flags_update_skb(u32 flags, struct sk_buff *skb, void *traits)
+{
+	if (flags & XDP_FLAGS_TRAITS_SUPPORTED)
+		skb_ext_from_headroom(skb, SKB_EXT_TRAITS, _XDP_FRAME_SIZE, traits_size(traits));
+}
+
+static __always_inline void xdp_buff_update_skb(const struct xdp_buff *xdp, struct sk_buff *skb)
+{
+	__xdp_flags_update_skb(xdp->flags, skb, xdp_buff_traits(xdp));
+}
+
 static __always_inline void
 xdp_init_buff(struct xdp_buff *xdp, u32 frame_sz, struct xdp_rxq_info *rxq)
 {
@@ -302,6 +313,16 @@ xdp_frame_is_frag_pfmemalloc(const struct xdp_frame *frame)
 	return !!(frame->flags & XDP_FLAGS_FRAGS_PF_MEMALLOC);
 }
 
+static void *xdp_frame_traits(const struct xdp_frame *frame)
+{
+	return frame->data + _XDP_FRAME_SIZE;
+}
+
+static __always_inline void xdp_frame_update_skb(struct xdp_frame *frame, struct sk_buff *skb)
+{
+	__xdp_flags_update_skb(frame->flags, skb, xdp_frame_traits(frame));
+}
+
 #define XDP_BULK_QUEUE_SIZE	16
 struct xdp_frame_bulk {
 	int count;
diff --git a/net/core/skbuff.c b/net/core/skbuff.c
index 34dae26dac4cea448f84dacabdc8fb6f4ac3c1a6..9f27caba82af0be7897b68b5fad087f3e9c62955 100644
--- a/net/core/skbuff.c
+++ b/net/core/skbuff.c
@@ -5043,6 +5043,10 @@ static const u8 skb_ext_type_len[] = {
 #if IS_ENABLED(CONFIG_MCTP_FLOWS)
 	[SKB_EXT_MCTP] = SKB_EXT_CHUNKSIZEOF(struct mctp_flow),
 #endif
+	/* TODO: skb_ext is slab allocated with room for all extensions,
+	 * this makes it a LOT bigger.
+	 */
+	[SKB_EXT_TRAITS] = SKB_EXT_CHUNKS(XDP_PACKET_HEADROOM),
 };
 
 static __always_inline unsigned int skb_ext_alloc_length(void)

-- 
2.43.0


Powered by blists - more mailing lists

Powered by Openwall GNU/*/Linux Powered by OpenVZ