diff options
| -rw-r--r-- | net/ipv4/devinet.c | 6 |
1 files changed, 5 insertions, 1 deletions
diff --git a/net/ipv4/devinet.c b/net/ipv4/devinet.c index 914ccc7f192a..6fd4628d10b9 100644 --- a/net/ipv4/devinet.c +++ b/net/ipv4/devinet.c | |||
| @@ -1287,6 +1287,7 @@ __be32 inet_select_addr(const struct net_device *dev, __be32 dst, int scope) | |||
| 1287 | { | 1287 | { |
| 1288 | const struct in_ifaddr *ifa; | 1288 | const struct in_ifaddr *ifa; |
| 1289 | __be32 addr = 0; | 1289 | __be32 addr = 0; |
| 1290 | unsigned char localnet_scope = RT_SCOPE_HOST; | ||
| 1290 | struct in_device *in_dev; | 1291 | struct in_device *in_dev; |
| 1291 | struct net *net = dev_net(dev); | 1292 | struct net *net = dev_net(dev); |
| 1292 | int master_idx; | 1293 | int master_idx; |
| @@ -1296,10 +1297,13 @@ __be32 inet_select_addr(const struct net_device *dev, __be32 dst, int scope) | |||
| 1296 | if (!in_dev) | 1297 | if (!in_dev) |
| 1297 | goto no_in_dev; | 1298 | goto no_in_dev; |
| 1298 | 1299 | ||
| 1300 | if (unlikely(IN_DEV_ROUTE_LOCALNET(in_dev))) | ||
| 1301 | localnet_scope = RT_SCOPE_LINK; | ||
| 1302 | |||
| 1299 | in_dev_for_each_ifa_rcu(ifa, in_dev) { | 1303 | in_dev_for_each_ifa_rcu(ifa, in_dev) { |
| 1300 | if (ifa->ifa_flags & IFA_F_SECONDARY) | 1304 | if (ifa->ifa_flags & IFA_F_SECONDARY) |
| 1301 | continue; | 1305 | continue; |
| 1302 | if (ifa->ifa_scope > scope) | 1306 | if (min(ifa->ifa_scope, localnet_scope) > scope) |
| 1303 | continue; | 1307 | continue; |
| 1304 | if (!dst || inet_ifa_match(dst, ifa)) { | 1308 | if (!dst || inet_ifa_match(dst, ifa)) { |
| 1305 | addr = ifa->ifa_local; | 1309 | addr = ifa->ifa_local; |
