Commit c2d305e5 authored by Florian Westphal's avatar Florian Westphal Committed by Steffen Klassert

xfrm: remove input indirection from xfrm_mode

No need for any indirection or abstraction here, both functions
are pretty much the same and quite small, they also have no external
dependencies.

xfrm_prepare_input can then be made static.

With allmodconfig build, size increase of vmlinux is 25 byte:

Before:
   text   data     bss     dec      filename
15730207  6936924 4046908 26714039  vmlinux

After:
15730208  6936948 4046908 26714064 vmlinux

v2: Fix INET_XFRM_MODE_TRANSPORT name in is-enabled test (Sabrina Dubroca)
    change copied comment to refer to transport and network header,
    not skb->{h,nh}, which don't exist anymore. (Sabrina)
    make xfrm_prepare_input static (Eyal Birger)
Signed-off-by: default avatarFlorian Westphal <fw@strlen.de>
Reviewed-by: default avatarSabrina Dubroca <sd@queasysnail.net>
Signed-off-by: default avatarSteffen Klassert <steffen.klassert@secunet.com>
parent b45714b1
...@@ -436,16 +436,6 @@ struct xfrm_mode { ...@@ -436,16 +436,6 @@ struct xfrm_mode {
*/ */
int (*input2)(struct xfrm_state *x, struct sk_buff *skb); int (*input2)(struct xfrm_state *x, struct sk_buff *skb);
/*
* This is the actual input entry point.
*
* For transport mode and equivalent this would be identical to
* input2 (which does not need to be set). While tunnel mode
* and equivalent would set this to the tunnel encapsulation function
* xfrm4_prepare_input that would in turn call input2.
*/
int (*input)(struct xfrm_state *x, struct sk_buff *skb);
/* /*
* Add encapsulation header. * Add encapsulation header.
* *
...@@ -1606,7 +1596,6 @@ int xfrm_init_replay(struct xfrm_state *x); ...@@ -1606,7 +1596,6 @@ int xfrm_init_replay(struct xfrm_state *x);
int xfrm_state_mtu(struct xfrm_state *x, int mtu); int xfrm_state_mtu(struct xfrm_state *x, int mtu);
int __xfrm_init_state(struct xfrm_state *x, bool init_replay, bool offload); int __xfrm_init_state(struct xfrm_state *x, bool init_replay, bool offload);
int xfrm_init_state(struct xfrm_state *x); int xfrm_init_state(struct xfrm_state *x);
int xfrm_prepare_input(struct xfrm_state *x, struct sk_buff *skb);
int xfrm_input(struct sk_buff *skb, int nexthdr, __be32 spi, int encap_type); int xfrm_input(struct sk_buff *skb, int nexthdr, __be32 spi, int encap_type);
int xfrm_input_resume(struct sk_buff *skb, int nexthdr); int xfrm_input_resume(struct sk_buff *skb, int nexthdr);
int xfrm_trans_queue(struct sk_buff *skb, int xfrm_trans_queue(struct sk_buff *skb,
......
...@@ -128,7 +128,6 @@ static int xfrm4_beet_input(struct xfrm_state *x, struct sk_buff *skb) ...@@ -128,7 +128,6 @@ static int xfrm4_beet_input(struct xfrm_state *x, struct sk_buff *skb)
static struct xfrm_mode xfrm4_beet_mode = { static struct xfrm_mode xfrm4_beet_mode = {
.input2 = xfrm4_beet_input, .input2 = xfrm4_beet_input,
.input = xfrm_prepare_input,
.output2 = xfrm4_beet_output, .output2 = xfrm4_beet_output,
.output = xfrm4_prepare_output, .output = xfrm4_prepare_output,
.owner = THIS_MODULE, .owner = THIS_MODULE,
......
...@@ -35,28 +35,6 @@ static int xfrm4_transport_output(struct xfrm_state *x, struct sk_buff *skb) ...@@ -35,28 +35,6 @@ static int xfrm4_transport_output(struct xfrm_state *x, struct sk_buff *skb)
return 0; return 0;
} }
/* Remove encapsulation header.
*
* The IP header will be moved over the top of the encapsulation header.
*
* On entry, skb->h shall point to where the IP header should be and skb->nh
* shall be set to where the IP header currently is. skb->data shall point
* to the start of the payload.
*/
static int xfrm4_transport_input(struct xfrm_state *x, struct sk_buff *skb)
{
int ihl = skb->data - skb_transport_header(skb);
if (skb->transport_header != skb->network_header) {
memmove(skb_transport_header(skb),
skb_network_header(skb), ihl);
skb->network_header = skb->transport_header;
}
ip_hdr(skb)->tot_len = htons(skb->len + ihl);
skb_reset_transport_header(skb);
return 0;
}
static struct sk_buff *xfrm4_transport_gso_segment(struct xfrm_state *x, static struct sk_buff *xfrm4_transport_gso_segment(struct xfrm_state *x,
struct sk_buff *skb, struct sk_buff *skb,
netdev_features_t features) netdev_features_t features)
...@@ -87,7 +65,6 @@ static void xfrm4_transport_xmit(struct xfrm_state *x, struct sk_buff *skb) ...@@ -87,7 +65,6 @@ static void xfrm4_transport_xmit(struct xfrm_state *x, struct sk_buff *skb)
} }
static struct xfrm_mode xfrm4_transport_mode = { static struct xfrm_mode xfrm4_transport_mode = {
.input = xfrm4_transport_input,
.output = xfrm4_transport_output, .output = xfrm4_transport_output,
.gso_segment = xfrm4_transport_gso_segment, .gso_segment = xfrm4_transport_gso_segment,
.xmit = xfrm4_transport_xmit, .xmit = xfrm4_transport_xmit,
......
...@@ -123,7 +123,6 @@ static void xfrm4_mode_tunnel_xmit(struct xfrm_state *x, struct sk_buff *skb) ...@@ -123,7 +123,6 @@ static void xfrm4_mode_tunnel_xmit(struct xfrm_state *x, struct sk_buff *skb)
static struct xfrm_mode xfrm4_tunnel_mode = { static struct xfrm_mode xfrm4_tunnel_mode = {
.input2 = xfrm4_mode_tunnel_input, .input2 = xfrm4_mode_tunnel_input,
.input = xfrm_prepare_input,
.output2 = xfrm4_mode_tunnel_output, .output2 = xfrm4_mode_tunnel_output,
.output = xfrm4_prepare_output, .output = xfrm4_prepare_output,
.gso_segment = xfrm4_mode_tunnel_gso_segment, .gso_segment = xfrm4_mode_tunnel_gso_segment,
......
...@@ -104,7 +104,6 @@ static int xfrm6_beet_input(struct xfrm_state *x, struct sk_buff *skb) ...@@ -104,7 +104,6 @@ static int xfrm6_beet_input(struct xfrm_state *x, struct sk_buff *skb)
static struct xfrm_mode xfrm6_beet_mode = { static struct xfrm_mode xfrm6_beet_mode = {
.input2 = xfrm6_beet_input, .input2 = xfrm6_beet_input,
.input = xfrm_prepare_input,
.output2 = xfrm6_beet_output, .output2 = xfrm6_beet_output,
.output = xfrm6_prepare_output, .output = xfrm6_prepare_output,
.owner = THIS_MODULE, .owner = THIS_MODULE,
......
...@@ -40,29 +40,6 @@ static int xfrm6_transport_output(struct xfrm_state *x, struct sk_buff *skb) ...@@ -40,29 +40,6 @@ static int xfrm6_transport_output(struct xfrm_state *x, struct sk_buff *skb)
return 0; return 0;
} }
/* Remove encapsulation header.
*
* The IP header will be moved over the top of the encapsulation header.
*
* On entry, skb->h shall point to where the IP header should be and skb->nh
* shall be set to where the IP header currently is. skb->data shall point
* to the start of the payload.
*/
static int xfrm6_transport_input(struct xfrm_state *x, struct sk_buff *skb)
{
int ihl = skb->data - skb_transport_header(skb);
if (skb->transport_header != skb->network_header) {
memmove(skb_transport_header(skb),
skb_network_header(skb), ihl);
skb->network_header = skb->transport_header;
}
ipv6_hdr(skb)->payload_len = htons(skb->len + ihl -
sizeof(struct ipv6hdr));
skb_reset_transport_header(skb);
return 0;
}
static struct sk_buff *xfrm4_transport_gso_segment(struct xfrm_state *x, static struct sk_buff *xfrm4_transport_gso_segment(struct xfrm_state *x,
struct sk_buff *skb, struct sk_buff *skb,
netdev_features_t features) netdev_features_t features)
...@@ -92,9 +69,7 @@ static void xfrm6_transport_xmit(struct xfrm_state *x, struct sk_buff *skb) ...@@ -92,9 +69,7 @@ static void xfrm6_transport_xmit(struct xfrm_state *x, struct sk_buff *skb)
} }
} }
static struct xfrm_mode xfrm6_transport_mode = { static struct xfrm_mode xfrm6_transport_mode = {
.input = xfrm6_transport_input,
.output = xfrm6_transport_output, .output = xfrm6_transport_output,
.gso_segment = xfrm4_transport_gso_segment, .gso_segment = xfrm4_transport_gso_segment,
.xmit = xfrm6_transport_xmit, .xmit = xfrm6_transport_xmit,
......
...@@ -122,7 +122,6 @@ static void xfrm6_mode_tunnel_xmit(struct xfrm_state *x, struct sk_buff *skb) ...@@ -122,7 +122,6 @@ static void xfrm6_mode_tunnel_xmit(struct xfrm_state *x, struct sk_buff *skb)
static struct xfrm_mode xfrm6_tunnel_mode = { static struct xfrm_mode xfrm6_tunnel_mode = {
.input2 = xfrm6_mode_tunnel_input, .input2 = xfrm6_mode_tunnel_input,
.input = xfrm_prepare_input,
.output2 = xfrm6_mode_tunnel_output, .output2 = xfrm6_mode_tunnel_output,
.output = xfrm6_prepare_output, .output = xfrm6_prepare_output,
.gso_segment = xfrm6_mode_tunnel_gso_segment, .gso_segment = xfrm6_mode_tunnel_gso_segment,
......
...@@ -166,7 +166,7 @@ int xfrm_parse_spi(struct sk_buff *skb, u8 nexthdr, __be32 *spi, __be32 *seq) ...@@ -166,7 +166,7 @@ int xfrm_parse_spi(struct sk_buff *skb, u8 nexthdr, __be32 *spi, __be32 *seq)
} }
EXPORT_SYMBOL(xfrm_parse_spi); EXPORT_SYMBOL(xfrm_parse_spi);
int xfrm_prepare_input(struct xfrm_state *x, struct sk_buff *skb) static int xfrm_prepare_input(struct xfrm_state *x, struct sk_buff *skb)
{ {
struct xfrm_mode *inner_mode = x->inner_mode; struct xfrm_mode *inner_mode = x->inner_mode;
int err; int err;
...@@ -184,7 +184,76 @@ int xfrm_prepare_input(struct xfrm_state *x, struct sk_buff *skb) ...@@ -184,7 +184,76 @@ int xfrm_prepare_input(struct xfrm_state *x, struct sk_buff *skb)
skb->protocol = inner_mode->afinfo->eth_proto; skb->protocol = inner_mode->afinfo->eth_proto;
return inner_mode->input2(x, skb); return inner_mode->input2(x, skb);
} }
EXPORT_SYMBOL(xfrm_prepare_input);
/* Remove encapsulation header.
*
* The IP header will be moved over the top of the encapsulation header.
*
* On entry, skb_transport_header() shall point to where the IP header
* should be and skb_network_header() shall be set to where the IP header
* currently is. skb->data shall point to the start of the payload.
*/
static int xfrm4_transport_input(struct xfrm_state *x, struct sk_buff *skb)
{
#if IS_ENABLED(CONFIG_INET_XFRM_MODE_TRANSPORT)
int ihl = skb->data - skb_transport_header(skb);
if (skb->transport_header != skb->network_header) {
memmove(skb_transport_header(skb),
skb_network_header(skb), ihl);
skb->network_header = skb->transport_header;
}
ip_hdr(skb)->tot_len = htons(skb->len + ihl);
skb_reset_transport_header(skb);
return 0;
#else
return -EOPNOTSUPP;
#endif
}
static int xfrm6_transport_input(struct xfrm_state *x, struct sk_buff *skb)
{
#if IS_ENABLED(CONFIG_INET6_XFRM_MODE_TRANSPORT)
int ihl = skb->data - skb_transport_header(skb);
if (skb->transport_header != skb->network_header) {
memmove(skb_transport_header(skb),
skb_network_header(skb), ihl);
skb->network_header = skb->transport_header;
}
ipv6_hdr(skb)->payload_len = htons(skb->len + ihl -
sizeof(struct ipv6hdr));
skb_reset_transport_header(skb);
return 0;
#else
return -EOPNOTSUPP;
#endif
}
static int xfrm_inner_mode_input(struct xfrm_state *x,
const struct xfrm_mode *inner_mode,
struct sk_buff *skb)
{
switch (inner_mode->encap) {
case XFRM_MODE_BEET:
case XFRM_MODE_TUNNEL:
return xfrm_prepare_input(x, skb);
case XFRM_MODE_TRANSPORT:
if (inner_mode->family == AF_INET)
return xfrm4_transport_input(x, skb);
if (inner_mode->family == AF_INET6)
return xfrm6_transport_input(x, skb);
break;
case XFRM_MODE_ROUTEOPTIMIZATION:
WARN_ON_ONCE(1);
break;
default:
WARN_ON_ONCE(1);
break;
}
return -EOPNOTSUPP;
}
int xfrm_input(struct sk_buff *skb, int nexthdr, __be32 spi, int encap_type) int xfrm_input(struct sk_buff *skb, int nexthdr, __be32 spi, int encap_type)
{ {
...@@ -410,7 +479,7 @@ int xfrm_input(struct sk_buff *skb, int nexthdr, __be32 spi, int encap_type) ...@@ -410,7 +479,7 @@ int xfrm_input(struct sk_buff *skb, int nexthdr, __be32 spi, int encap_type)
} }
} }
if (inner_mode->input(x, skb)) { if (xfrm_inner_mode_input(x, inner_mode, skb)) {
XFRM_INC_STATS(net, LINUX_MIB_XFRMINSTATEMODEERROR); XFRM_INC_STATS(net, LINUX_MIB_XFRMINSTATEMODEERROR);
goto drop; goto drop;
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment