mirror of https://gitee.com/openkylin/linux.git
[IPV6]: Fix source address selection for ORCHID addresses
Skip the prefix length matching in source address selection for orchid -> non-orchid addresses. Overlay Routable Cryptographic Hash IDentifiers (RFC 4843, 2001:10::/28) are currenty not globally reachable. Without this check a host with an ORCHID address can end up preferring those over regular addresses when talking to other regular hosts in the 2001::/16 range thus breaking non-orchid connections. Signed-off-by: Juha-Matti Tapio <jmtapio@verkkotelakka.net> Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
parent
5fe47b8a65
commit
99cd07a537
|
@ -383,6 +383,16 @@ static inline int ipv6_addr_v4mapped(const struct in6_addr *a)
|
||||||
a->s6_addr32[2] == htonl(0x0000ffff));
|
a->s6_addr32[2] == htonl(0x0000ffff));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Check for a RFC 4843 ORCHID address
|
||||||
|
* (Overlay Routable Cryptographic Hash Identifiers)
|
||||||
|
*/
|
||||||
|
static inline int ipv6_addr_orchid(const struct in6_addr *a)
|
||||||
|
{
|
||||||
|
return ((a->s6_addr32[0] & htonl(0xfffffff0))
|
||||||
|
== htonl(0x20010010));
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* find the first different bit between two addresses
|
* find the first different bit between two addresses
|
||||||
* length of address must be a multiple of 32bits
|
* length of address must be a multiple of 32bits
|
||||||
|
|
|
@ -1125,6 +1125,11 @@ int ipv6_dev_get_saddr(struct net_device *daddr_dev,
|
||||||
if (hiscore.rule < 7)
|
if (hiscore.rule < 7)
|
||||||
hiscore.rule++;
|
hiscore.rule++;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
/* Skip rule 8 for orchid -> non-orchid address pairs. */
|
||||||
|
if (ipv6_addr_orchid(&ifa->addr) && !ipv6_addr_orchid(daddr))
|
||||||
|
continue;
|
||||||
|
|
||||||
/* Rule 8: Use longest matching prefix */
|
/* Rule 8: Use longest matching prefix */
|
||||||
if (hiscore.rule < 8) {
|
if (hiscore.rule < 8) {
|
||||||
hiscore.matchlen = ipv6_addr_diff(&ifa_result->addr, daddr);
|
hiscore.matchlen = ipv6_addr_diff(&ifa_result->addr, daddr);
|
||||||
|
|
Loading…
Reference in New Issue