Commit 3789caba authored by Shmulik Ladkani's avatar Shmulik Ladkani Committed by David S. Miller

ip6_tunnel: collect_md xmit: Use ip_tunnel_key's provided src address

When using an ip6tnl device in collect_md mode, the xmit methods ignore
the ipv6.src field present in skb_tunnel_info's key, both for route
calculation purposes (flowi6 construction) and for assigning the
packet's final ipv6h->saddr.

This makes it impossible specifying a desired ipv6 local address in the
encapsulating header (for example, when using tc action tunnel_key).

This is also not aligned with behavior of ipip (ipv4) in collect_md
mode, where the key->u.ipv4.src gets used.

Fix, by assigning fl6.saddr with given key->u.ipv6.src.
In case ipv6.src is not specified, ip6_tnl_xmit uses existing saddr
selection code.

Fixes: 8d79266b ("ip6_tunnel: add collect_md mode to IPv6 tunnels")
Signed-off-by: default avatarShmulik Ladkani <shmulik.ladkani@gmail.com>
Reviewed-by: default avatarEyal Birger <eyal.birger@gmail.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 9ca61630
...@@ -1113,7 +1113,7 @@ int ip6_tnl_xmit(struct sk_buff *skb, struct net_device *dev, __u8 dsfield, ...@@ -1113,7 +1113,7 @@ int ip6_tnl_xmit(struct sk_buff *skb, struct net_device *dev, __u8 dsfield,
dst = NULL; dst = NULL;
goto tx_err_link_failure; goto tx_err_link_failure;
} }
if (t->parms.collect_md && if (t->parms.collect_md && ipv6_addr_any(&fl6->saddr) &&
ipv6_dev_get_saddr(net, ip6_dst_idev(dst)->dev, ipv6_dev_get_saddr(net, ip6_dst_idev(dst)->dev,
&fl6->daddr, 0, &fl6->saddr)) &fl6->daddr, 0, &fl6->saddr))
goto tx_err_link_failure; goto tx_err_link_failure;
...@@ -1255,6 +1255,7 @@ ip4ip6_tnl_xmit(struct sk_buff *skb, struct net_device *dev) ...@@ -1255,6 +1255,7 @@ ip4ip6_tnl_xmit(struct sk_buff *skb, struct net_device *dev)
key = &tun_info->key; key = &tun_info->key;
memset(&fl6, 0, sizeof(fl6)); memset(&fl6, 0, sizeof(fl6));
fl6.flowi6_proto = IPPROTO_IPIP; fl6.flowi6_proto = IPPROTO_IPIP;
fl6.saddr = key->u.ipv6.src;
fl6.daddr = key->u.ipv6.dst; fl6.daddr = key->u.ipv6.dst;
fl6.flowlabel = key->label; fl6.flowlabel = key->label;
dsfield = key->tos; dsfield = key->tos;
...@@ -1326,6 +1327,7 @@ ip6ip6_tnl_xmit(struct sk_buff *skb, struct net_device *dev) ...@@ -1326,6 +1327,7 @@ ip6ip6_tnl_xmit(struct sk_buff *skb, struct net_device *dev)
key = &tun_info->key; key = &tun_info->key;
memset(&fl6, 0, sizeof(fl6)); memset(&fl6, 0, sizeof(fl6));
fl6.flowi6_proto = IPPROTO_IPV6; fl6.flowi6_proto = IPPROTO_IPV6;
fl6.saddr = key->u.ipv6.src;
fl6.daddr = key->u.ipv6.dst; fl6.daddr = key->u.ipv6.dst;
fl6.flowlabel = key->label; fl6.flowlabel = key->label;
dsfield = key->tos; dsfield = key->tos;
......
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