diff options
Diffstat (limited to 'net/ipv6/route.c')
-rw-r--r-- | net/ipv6/route.c | 19 |
1 files changed, 12 insertions, 7 deletions
diff --git a/net/ipv6/route.c b/net/ipv6/route.c index 0607ee3a0eac..d1ddbc6ddac5 100644 --- a/net/ipv6/route.c +++ b/net/ipv6/route.c | |||
@@ -226,7 +226,7 @@ static const struct rt6_info ip6_null_entry_template = { | |||
226 | .dst = { | 226 | .dst = { |
227 | .__refcnt = ATOMIC_INIT(1), | 227 | .__refcnt = ATOMIC_INIT(1), |
228 | .__use = 1, | 228 | .__use = 1, |
229 | .obsolete = -1, | 229 | .obsolete = DST_OBSOLETE_FORCE_CHK, |
230 | .error = -ENETUNREACH, | 230 | .error = -ENETUNREACH, |
231 | .input = ip6_pkt_discard, | 231 | .input = ip6_pkt_discard, |
232 | .output = ip6_pkt_discard_out, | 232 | .output = ip6_pkt_discard_out, |
@@ -246,7 +246,7 @@ static const struct rt6_info ip6_prohibit_entry_template = { | |||
246 | .dst = { | 246 | .dst = { |
247 | .__refcnt = ATOMIC_INIT(1), | 247 | .__refcnt = ATOMIC_INIT(1), |
248 | .__use = 1, | 248 | .__use = 1, |
249 | .obsolete = -1, | 249 | .obsolete = DST_OBSOLETE_FORCE_CHK, |
250 | .error = -EACCES, | 250 | .error = -EACCES, |
251 | .input = ip6_pkt_prohibit, | 251 | .input = ip6_pkt_prohibit, |
252 | .output = ip6_pkt_prohibit_out, | 252 | .output = ip6_pkt_prohibit_out, |
@@ -261,7 +261,7 @@ static const struct rt6_info ip6_blk_hole_entry_template = { | |||
261 | .dst = { | 261 | .dst = { |
262 | .__refcnt = ATOMIC_INIT(1), | 262 | .__refcnt = ATOMIC_INIT(1), |
263 | .__use = 1, | 263 | .__use = 1, |
264 | .obsolete = -1, | 264 | .obsolete = DST_OBSOLETE_FORCE_CHK, |
265 | .error = -EINVAL, | 265 | .error = -EINVAL, |
266 | .input = dst_discard, | 266 | .input = dst_discard, |
267 | .output = dst_discard, | 267 | .output = dst_discard, |
@@ -281,13 +281,14 @@ static inline struct rt6_info *ip6_dst_alloc(struct net *net, | |||
281 | struct fib6_table *table) | 281 | struct fib6_table *table) |
282 | { | 282 | { |
283 | struct rt6_info *rt = dst_alloc(&net->ipv6.ip6_dst_ops, dev, | 283 | struct rt6_info *rt = dst_alloc(&net->ipv6.ip6_dst_ops, dev, |
284 | 0, DST_OBSOLETE_NONE, flags); | 284 | 0, DST_OBSOLETE_FORCE_CHK, flags); |
285 | 285 | ||
286 | if (rt) { | 286 | if (rt) { |
287 | struct dst_entry *dst = &rt->dst; | 287 | struct dst_entry *dst = &rt->dst; |
288 | 288 | ||
289 | memset(dst + 1, 0, sizeof(*rt) - sizeof(*dst)); | 289 | memset(dst + 1, 0, sizeof(*rt) - sizeof(*dst)); |
290 | rt6_init_peer(rt, table ? &table->tb6_peers : net->ipv6.peers); | 290 | rt6_init_peer(rt, table ? &table->tb6_peers : net->ipv6.peers); |
291 | rt->rt6i_genid = rt_genid(net); | ||
291 | } | 292 | } |
292 | return rt; | 293 | return rt; |
293 | } | 294 | } |
@@ -1022,6 +1023,13 @@ static struct dst_entry *ip6_dst_check(struct dst_entry *dst, u32 cookie) | |||
1022 | 1023 | ||
1023 | rt = (struct rt6_info *) dst; | 1024 | rt = (struct rt6_info *) dst; |
1024 | 1025 | ||
1026 | /* All IPV6 dsts are created with ->obsolete set to the value | ||
1027 | * DST_OBSOLETE_FORCE_CHK which forces validation calls down | ||
1028 | * into this function always. | ||
1029 | */ | ||
1030 | if (rt->rt6i_genid != rt_genid(dev_net(rt->dst.dev))) | ||
1031 | return NULL; | ||
1032 | |||
1025 | if (rt->rt6i_node && (rt->rt6i_node->fn_sernum == cookie)) { | 1033 | if (rt->rt6i_node && (rt->rt6i_node->fn_sernum == cookie)) { |
1026 | if (rt->rt6i_peer_genid != rt6_peer_genid()) { | 1034 | if (rt->rt6i_peer_genid != rt6_peer_genid()) { |
1027 | if (!rt6_has_peer(rt)) | 1035 | if (!rt6_has_peer(rt)) |
@@ -1388,8 +1396,6 @@ int ip6_route_add(struct fib6_config *cfg) | |||
1388 | goto out; | 1396 | goto out; |
1389 | } | 1397 | } |
1390 | 1398 | ||
1391 | rt->dst.obsolete = -1; | ||
1392 | |||
1393 | if (cfg->fc_flags & RTF_EXPIRES) | 1399 | if (cfg->fc_flags & RTF_EXPIRES) |
1394 | rt6_set_expires(rt, jiffies + | 1400 | rt6_set_expires(rt, jiffies + |
1395 | clock_t_to_jiffies(cfg->fc_expires)); | 1401 | clock_t_to_jiffies(cfg->fc_expires)); |
@@ -2084,7 +2090,6 @@ struct rt6_info *addrconf_dst_alloc(struct inet6_dev *idev, | |||
2084 | rt->dst.input = ip6_input; | 2090 | rt->dst.input = ip6_input; |
2085 | rt->dst.output = ip6_output; | 2091 | rt->dst.output = ip6_output; |
2086 | rt->rt6i_idev = idev; | 2092 | rt->rt6i_idev = idev; |
2087 | rt->dst.obsolete = -1; | ||
2088 | 2093 | ||
2089 | rt->rt6i_flags = RTF_UP | RTF_NONEXTHOP; | 2094 | rt->rt6i_flags = RTF_UP | RTF_NONEXTHOP; |
2090 | if (anycast) | 2095 | if (anycast) |