diff mbox series

[net-next,1/3] net: gso: add HBH extension header offload support

Message ID e8b01e54-b623-44ec-84d5-406ea3b0c80b@gmail.com
State Superseded
Headers show
Series net: gro: reduce extension header parsing overhead | expand

Commit Message

Richard Gobert Dec. 21, 2023, 6:55 p.m. UTC
This commit adds net_offload to IPv6 Hop-by-Hop extension headers (as it
is done for routing and dstopts) since it is supported in GSO and GRO.
This allows to remove specific HBH conditionals in GSO and GRO when
pulling and parsing an incoming packet.

Signed-off-by: Richard Gobert <richardbgobert@gmail.com>
---
 net/ipv6/exthdrs_offload.c | 11 +++++++++++
 net/ipv6/ip6_offload.c     | 25 +++++++++++--------------
 2 files changed, 22 insertions(+), 14 deletions(-)

Comments

Willem de Bruijn Dec. 26, 2023, 8:24 p.m. UTC | #1
Richard Gobert wrote:
> This commit adds net_offload to IPv6 Hop-by-Hop extension headers (as it
> is done for routing and dstopts) since it is supported in GSO and GRO.
> This allows to remove specific HBH conditionals in GSO and GRO when
> pulling and parsing an incoming packet.
> 
> Signed-off-by: Richard Gobert <richardbgobert@gmail.com>

Reviewed-by: Willem de Bruijn <willemb@google.com>

> ---
>  net/ipv6/exthdrs_offload.c | 11 +++++++++++
>  net/ipv6/ip6_offload.c     | 25 +++++++++++--------------
>  2 files changed, 22 insertions(+), 14 deletions(-)
> 
> diff --git a/net/ipv6/exthdrs_offload.c b/net/ipv6/exthdrs_offload.c
> index 06750d65d480..4c00398f4dca 100644
> --- a/net/ipv6/exthdrs_offload.c
> +++ b/net/ipv6/exthdrs_offload.c
> @@ -16,6 +16,10 @@ static const struct net_offload dstopt_offload = {
>  	.flags		=	INET6_PROTO_GSO_EXTHDR,
>  };
>  
> +static const struct net_offload hbh_offload = {
> +	.flags		=	INET6_PROTO_GSO_EXTHDR,
> +};
> +
>  int __init ipv6_exthdrs_offload_init(void)
>  {
>  	int ret;
> @@ -28,9 +32,16 @@ int __init ipv6_exthdrs_offload_init(void)
>  	if (ret)
>  		goto out_rt;
>  
> +	ret = inet6_add_offload(&hbh_offload, IPPROTO_HOPOPTS);
> +	if (ret)
> +		goto out_dstopts;
> +
>  out:
>  	return ret;
>  
> +out_dstopts:
> +	inet6_del_offload(&dstopt_offload, IPPROTO_DSTOPTS);
> +
>  out_rt:
>  	inet6_del_offload(&rthdr_offload, IPPROTO_ROUTING);
>  	goto out;
> diff --git a/net/ipv6/ip6_offload.c b/net/ipv6/ip6_offload.c
> index d6314287338d..0e0b5fed0995 100644
> --- a/net/ipv6/ip6_offload.c
> +++ b/net/ipv6/ip6_offload.c
> @@ -45,15 +45,13 @@ static int ipv6_gso_pull_exthdrs(struct sk_buff *skb, int proto)
>  		struct ipv6_opt_hdr *opth;
>  		int len;
>  
> -		if (proto != NEXTHDR_HOP) {
> -			ops = rcu_dereference(inet6_offloads[proto]);
> +		ops = rcu_dereference(inet6_offloads[proto]);
>  
> -			if (unlikely(!ops))
> -				break;
> +		if (unlikely(!ops))
> +			break;
>  
> -			if (!(ops->flags & INET6_PROTO_GSO_EXTHDR))
> -				break;
> -		}
> +		if (!(ops->flags & INET6_PROTO_GSO_EXTHDR))
> +			break;
>  
>  		if (unlikely(!pskb_may_pull(skb, 8)))
>  			break;
> @@ -171,13 +169,12 @@ static int ipv6_exthdrs_len(struct ipv6hdr *iph,
>  
>  	proto = iph->nexthdr;
>  	for (;;) {
> -		if (proto != NEXTHDR_HOP) {
> -			*opps = rcu_dereference(inet6_offloads[proto]);
> -			if (unlikely(!(*opps)))
> -				break;
> -			if (!((*opps)->flags & INET6_PROTO_GSO_EXTHDR))
> -				break;
> -		}
> +		*opps = rcu_dereference(inet6_offloads[proto]);
> +		if (unlikely(!(*opps)))
> +			break;
> +		if (!((*opps)->flags & INET6_PROTO_GSO_EXTHDR))
> +			break;
> +
>  		opth = (void *)opth + optlen;
>  		optlen = ipv6_optlen(opth);
>  		len += optlen;
> -- 
> 2.36.1
>
diff mbox series

Patch

diff --git a/net/ipv6/exthdrs_offload.c b/net/ipv6/exthdrs_offload.c
index 06750d65d480..4c00398f4dca 100644
--- a/net/ipv6/exthdrs_offload.c
+++ b/net/ipv6/exthdrs_offload.c
@@ -16,6 +16,10 @@  static const struct net_offload dstopt_offload = {
 	.flags		=	INET6_PROTO_GSO_EXTHDR,
 };
 
+static const struct net_offload hbh_offload = {
+	.flags		=	INET6_PROTO_GSO_EXTHDR,
+};
+
 int __init ipv6_exthdrs_offload_init(void)
 {
 	int ret;
@@ -28,9 +32,16 @@  int __init ipv6_exthdrs_offload_init(void)
 	if (ret)
 		goto out_rt;
 
+	ret = inet6_add_offload(&hbh_offload, IPPROTO_HOPOPTS);
+	if (ret)
+		goto out_dstopts;
+
 out:
 	return ret;
 
+out_dstopts:
+	inet6_del_offload(&dstopt_offload, IPPROTO_DSTOPTS);
+
 out_rt:
 	inet6_del_offload(&rthdr_offload, IPPROTO_ROUTING);
 	goto out;
diff --git a/net/ipv6/ip6_offload.c b/net/ipv6/ip6_offload.c
index d6314287338d..0e0b5fed0995 100644
--- a/net/ipv6/ip6_offload.c
+++ b/net/ipv6/ip6_offload.c
@@ -45,15 +45,13 @@  static int ipv6_gso_pull_exthdrs(struct sk_buff *skb, int proto)
 		struct ipv6_opt_hdr *opth;
 		int len;
 
-		if (proto != NEXTHDR_HOP) {
-			ops = rcu_dereference(inet6_offloads[proto]);
+		ops = rcu_dereference(inet6_offloads[proto]);
 
-			if (unlikely(!ops))
-				break;
+		if (unlikely(!ops))
+			break;
 
-			if (!(ops->flags & INET6_PROTO_GSO_EXTHDR))
-				break;
-		}
+		if (!(ops->flags & INET6_PROTO_GSO_EXTHDR))
+			break;
 
 		if (unlikely(!pskb_may_pull(skb, 8)))
 			break;
@@ -171,13 +169,12 @@  static int ipv6_exthdrs_len(struct ipv6hdr *iph,
 
 	proto = iph->nexthdr;
 	for (;;) {
-		if (proto != NEXTHDR_HOP) {
-			*opps = rcu_dereference(inet6_offloads[proto]);
-			if (unlikely(!(*opps)))
-				break;
-			if (!((*opps)->flags & INET6_PROTO_GSO_EXTHDR))
-				break;
-		}
+		*opps = rcu_dereference(inet6_offloads[proto]);
+		if (unlikely(!(*opps)))
+			break;
+		if (!((*opps)->flags & INET6_PROTO_GSO_EXTHDR))
+			break;
+
 		opth = (void *)opth + optlen;
 		optlen = ipv6_optlen(opth);
 		len += optlen;