Message ID | 20210318184157.700604-3-alobakin@pm.me |
---|---|
State | New |
Headers | show |
Series | net: avoid retpoline overhead on VLAN and TEB GRO | expand |
Hello, On Thu, 2021-03-18 at 18:42 +0000, Alexander Lobakin wrote: > call_gro_receive() is used to limit GRO recursion, but it works only > with callback pointers. > There's a combined version of call_gro_receive() + INDIRECT_CALL_2() > in <net/inet_common.h>, but it doesn't check for IPv6 modularity. AFAICS, ip6_offload is builtin even when IPv6 is a module, so the above should not be needed. Cheers, Paolo
From: Paolo Abeni <pabeni@redhat.com> Date: Fri, 19 Mar 2021 11:53:42 +0100 > Hello, Hi! > On Thu, 2021-03-18 at 18:42 +0000, Alexander Lobakin wrote: > > call_gro_receive() is used to limit GRO recursion, but it works only > > with callback pointers. > > There's a combined version of call_gro_receive() + INDIRECT_CALL_2() > > in <net/inet_common.h>, but it doesn't check for IPv6 modularity. > > AFAICS, ip6_offload is builtin even when IPv6 is a module, so the above > should not be needed. Aww, you are right. I overlooked that since dev_gro_receive() still use INDIRECT_CALL_INET(), though all GRO callbacks were made built-in. Seems like more code can be optimized, thanks! > Cheers, > > Paolo Al
From: Alexander Lobakin <alobakin@pm.me> Date: Fri, 19 Mar 2021 11:13:25 +0000 > From: Paolo Abeni <pabeni@redhat.com> > Date: Fri, 19 Mar 2021 11:53:42 +0100 > > > Hello, > > Hi! > > > On Thu, 2021-03-18 at 18:42 +0000, Alexander Lobakin wrote: > > > call_gro_receive() is used to limit GRO recursion, but it works only > > > with callback pointers. > > > There's a combined version of call_gro_receive() + INDIRECT_CALL_2() > > > in <net/inet_common.h>, but it doesn't check for IPv6 modularity. > > > > AFAICS, ip6_offload is builtin even when IPv6 is a module, so the above > > should not be needed. > > Aww, you are right. I overlooked that since dev_gro_receive() still > use INDIRECT_CALL_INET(), though all GRO callbacks were made > built-in. I'm not sure if you did it on purpose in commit aaa5d90b395a7 ("net: use indirect call wrappers at GRO network layer"). Was that intentional for the sake of more optimized path for the kernels with moduled IPv6, or I can replace INDIRECT_CALL_INET() with INDIRECT_CALL_2() here too? I want to keep GRO callbacks that make use of indirect call wrappers unified. > Seems like more code can be optimized, thanks! > > > Cheers, > > > > Paolo > > Al Thanks, Al
On Fri, 2021-03-19 at 11:43 +0000, Alexander Lobakin wrote: > I'm not sure if you did it on purpose in commit aaa5d90b395a7 > ("net: use indirect call wrappers at GRO network layer"). > Was that intentional I must admit that 2y+ later my own intentions are not so clear to me too;) > for the sake of more optimized path for the > kernels with moduled IPv6, Uhm... no I guess that was more an underlook on my side. > or I can replace INDIRECT_CALL_INET() > with INDIRECT_CALL_2() here too? If that build with IPV6=nmy, I would say yes. > I want to keep GRO callbacks that > make use of indirect call wrappers unified. L4 will still need some special handling as ipv6 udp gro callbacks are not builtin with CONFIG_IPV6=m :( Cheers, Paolo
From: Paolo Abeni <pabeni@redhat.com> Date: Fri, 19 Mar 2021 13:35:41 +0100 > On Fri, 2021-03-19 at 11:43 +0000, Alexander Lobakin wrote: > > I'm not sure if you did it on purpose in commit aaa5d90b395a7 > > ("net: use indirect call wrappers at GRO network layer"). > > Was that intentional > > I must admit that 2y+ later my own intentions are not so clear to me > too;) Heh, know that feel (= > > for the sake of more optimized path for the > > kernels with moduled IPv6, > > Uhm... no I guess that was more an underlook on my side. > > > or I can replace INDIRECT_CALL_INET() > > with INDIRECT_CALL_2() here too? > > If that build with IPV6=nmy, I would say yes. I think you used INDIRECT_CALL_INET() to protect from CONFIG_INET=n. But this also hurts with retpoline when CONFIG_IPV6=m. Not so common case, but still. Plain INDIRECT_CALL_2() won't build without CONFIG_INET, so we either introduce a new one (e.g. _INET_2() similarly to _INET_1()), or leave it as it is for now (Dave's already picked this series to net-next). > > I want to keep GRO callbacks that > > make use of indirect call wrappers unified. > > L4 will still need some special handling as ipv6 udp gro callbacks are > not builtin with CONFIG_IPV6=m :( Yep, I remember. I meant {inet,ipv6}_gro_{complete,receive}() callers, but didn't mention that for some reason. > Cheers, > > Paolo Thanks, Al
diff --git a/include/net/gro.h b/include/net/gro.h index 27c38b36df16..01edaf3fdda0 100644 --- a/include/net/gro.h +++ b/include/net/gro.h @@ -14,4 +14,12 @@ INDIRECT_CALLABLE_DECLARE(int ipv6_gro_complete(struct sk_buff *, int)); INDIRECT_CALLABLE_DECLARE(struct sk_buff *inet_gro_receive(struct list_head *, struct sk_buff *)); INDIRECT_CALLABLE_DECLARE(int inet_gro_complete(struct sk_buff *, int)); + +#define indirect_call_gro_receive_inet(cb, f2, f1, head, skb) \ +({ \ + unlikely(gro_recursion_inc_test(skb)) ? \ + NAPI_GRO_CB(skb)->flush |= 1, NULL : \ + INDIRECT_CALL_INET(cb, f2, f1, head, skb); \ +}) + #endif /* _NET_IPV6_GRO_H */
call_gro_receive() is used to limit GRO recursion, but it works only with callback pointers. There's a combined version of call_gro_receive() + INDIRECT_CALL_2() in <net/inet_common.h>, but it doesn't check for IPv6 modularity. Add a similar new helper to cover both of these. It can and will be used to avoid retpoline overhead when IP header lies behind another offloaded proto. Signed-off-by: Alexander Lobakin <alobakin@pm.me> --- include/net/gro.h | 8 ++++++++ 1 file changed, 8 insertions(+) -- 2.31.0