On Fri, 18 Sep 2026 16:46:49 +0800
Wang Zhan <[email protected]> wrote:
> The bounded resegmentation added by the next patch splits an oversized TCP
> GSO skb into several GSO skbs which fit the device limits. That needs the
> GSO engine to group several MSS segments into one output skb, so let
> callers bound the number of MSS segments each output skb carries and pass
> the bound through the existing __skb_gso_segment() entry point. Ordinary
> callers use zero for no limit.
>
> skb_segment() only groups several MSS into one output skb when the device
> advertises NETIF_F_GSO_PARTIAL, or when the skb has a frag_list which can
> be split into uniform pieces, and falls back to one segment per skb
> otherwise. A caller which passes a bound asks for that grouping
> regardless, so the frag_list check is skipped when max_segs is set. Every
> other caller keeps it, and the bounded path is only used for skbs which do
> not carry a frag_list.
>
> The output stays a GSO skb: gso_size is the original MSS and gso_segs is
> the number of MSS it holds, so a downstream device can still perform
> ordinary TSO. Store the bound in the existing skb_gso_cb scratch context,
> alongside the call-local data_offset and mac_offset fields, so that the
> segmentation methods keep their signature. A zero max_segs value means
> that no bound is active; it is not a persistent skb flag. Clear the value
> when each output skb copies the input header so the temporary limit is not
> propagated to the next GSO call.
>
...
> @@ -86,7 +87,8 @@ static bool skb_needs_check(const struct sk_buff *skb, bool
> tx_path)
> * Segmentation preserves SKB_GSO_CB_OFFSET bytes of previous skb cb.
> */
> struct sk_buff *__skb_gso_segment(struct sk_buff *skb,
> - netdev_features_t features, bool tx_path)
> + netdev_features_t features, bool tx_path,
> + unsigned int max_segs)
> {
> struct sk_buff *segs;
>
> @@ -117,6 +119,7 @@ struct sk_buff *__skb_gso_segment(struct sk_buff *skb,
>
> SKB_GSO_CB(skb)->mac_offset = skb_headroom(skb);
> SKB_GSO_CB(skb)->encap_level = 0;
> + SKB_GSO_CB(skb)->max_segs = min_t(unsigned int, max_segs, U16_MAX);
Why min_t() ??
David
_______________________________________________
dev mailing list
[email protected]
https://mail.openvswitch.org/mailman/listinfo/ovs-dev